teratail header banner
teratail header banner
質問するログイン新規登録

回答編集履歴

2

誤記修正

2018/05/05 08:58

投稿

Thrush
Thrush

スコア58

answer CHANGED
@@ -5,7 +5,7 @@
5
5
  僕もElektrobitに問い合わせましたが、法人対応のみとのことで回答をもらえませんでした
6
6
 
7
7
  >そのファイルの特徴、他形式のものとの違い、プログラミング言語との親和性等が知りたいです。
8
- フォーマットはほぼxmlそのままですので、気合で読めると思います。
8
+ フォーマットはほぼjsonそのままですので、気合で読めると思います。
9
9
 
10
10
  ↓ここがプロパティの実体の宣言で
11
11
  ```ここに言語を入力

1

詳細の追記

2018/05/05 08:58

投稿

Thrush
Thrush

スコア58

answer CHANGED
@@ -1,3 +1,303 @@
1
1
  察するに、EBGuideのフォーマットですね
2
+
3
+ >gdata形式のファイルについて、具体的な取扱いに関する情報が載っているサイトをご存知ですか?
2
4
  フォーマットの情報は一般に公開されていません
5
+ 僕もElektrobitに問い合わせましたが、法人対応のみとのことで回答をもらえませんでした
6
+
7
+ >そのファイルの特徴、他形式のものとの違い、プログラミング言語との親和性等が知りたいです。
8
+ フォーマットはほぼxmlそのままですので、気合で読めると思います。
9
+
10
+ ↓ここがプロパティの実体の宣言で
11
+ ```ここに言語を入力
12
+ #2479056145 items :: dp_item_list : <object>
13
+ ```
14
+
15
+ ↓ここがオブジェクトの実体の宣言です。
16
+ ```
17
+ dp(int) : @de86b58e-a2a5-4779-b793-96c137480cc1
18
+ {
19
+ #3605065401 value :: int : 1;
20
+ #460587879 name :: string : "INT_test";
21
+ }
22
+ ```
23
+
24
+ 1つのプロパティは、オブジェクト、あるいは普通の数値や文字列を(通常)1つ持ちます。
25
+ 1つのオブジェクトは複数のプロパティを持ちます。
26
+ ただし、質問に記述されている例は1つのプロパティは複数のオブジェクトを配列として持つ特殊な例です。
27
+
3
- python(ply)やC++(flex/bison)でパースするしかないでしょう
28
+ 何らかの情報を抜き取りたい場合、python(ply)やC++(flex/bison)でパースするしかないと思います。
29
+ パーサジェネレータを使って遊んでいる人であれば、以下のコードが参考になるかもしれません。
30
+ (ちょっと前に書いてたやつなので、バグとかあったらごめんなさい)
31
+
32
+ ```python
33
+ #!/usr/bin/env python
34
+ import ply.lex as lex
35
+ from ply.lex import TOKEN
36
+
37
+ #
38
+ #PRINT = print
39
+ PRINT = lambda x : None
40
+
41
+ #---------------------------------------------------------------------
42
+ # define states
43
+ states = (
44
+ ('text', 'exclusive'),
45
+ ('version', 'exclusive'),
46
+ )
47
+
48
+ #---------------------------------------------------------------------
49
+ # define literals
50
+ literals = "()[]{}<>@#;,"
51
+
52
+ #---------------------------------------------------------------------
53
+ #define regular expression parts
54
+ def PAREN(t):
55
+ t = r'(' + t + r')'
56
+ return t
57
+ INTEGER_NUMBER_INTEGER = r'[+-]?[1-9][0-9]*[Ff]?|[+-]?0'
58
+ INTEGER_NUMBER_FLOAT = r'[+-]?[1-9][0-9]*[Ff]?|[+-]?0[fF]?'
59
+ INTEGER_NUMBER = PAREN(INTEGER_NUMBER_INTEGER) + "|" + PAREN(INTEGER_NUMBER_FLOAT );
60
+ REAL_NUMBER = PAREN(INTEGER_NUMBER_INTEGER) + r'?' + r'.[0-9]*[fF]?'
61
+ NUMBER = PAREN(REAL_NUMBER) + r'|' + PAREN(INTEGER_NUMBER)
62
+
63
+ #---------------------------------------------------------------------
64
+ # declare token
65
+ tokens = (
66
+ 'NUMBER',
67
+ 'EBGUIDE',
68
+ 'BOOL',
69
+ 'PROP_ID',
70
+ 'OBJ_ID',
71
+ "START_TEXT",
72
+ 'END_TEXT',
73
+ 'TEXT',
74
+ 'SYMBOL',
75
+ 'VERSION',
76
+ )
77
+
78
+ #---------------------------------------------------------------------
79
+ # defien ignore token
80
+ t_ignore = ' \t:'
81
+ t_text_ignore = ''
82
+ t_version_ignore = ''
83
+
84
+ #---------------------------------------------------------------------
85
+ # define token by RE
86
+ #t_EBGUIDE = r'EBGUIDE'
87
+
88
+ #---------------------------------------------------------------------
89
+ # define token as function by state
90
+
91
+ def t_ANY_newline(t):
92
+ r'\n+'
93
+ t.lexer.lineno += len(t.value)
94
+
95
+ @TOKEN(NUMBER)
96
+ def t_NUMBER(t):
97
+ PRINT(t.value)
98
+ t.value = t.value.replace("f", "")
99
+ t.value = t.value.replace("F", "")
100
+ t.value = float(t.value)
101
+ return t
102
+ def t_EBGUIDE(t):
103
+ r'EBGUIDE'
104
+ PRINT(t.value)
105
+ t.lexer.push_state("version")
106
+ return t
107
+ def t_BOOL(t):
108
+ r'true|false'
109
+ PRINT(t.value)
110
+ t.value = True if t.value == "true" else False
111
+ return t
112
+ def t_PROP_ID(t):
113
+ r'\#[0-9]+'
114
+ PRINT(t.value)
115
+ return t
116
+ def t_OBJ_ID(t):
117
+ r'@[a-zA-Z0-9\-]+'
118
+ PRINT(t.value)
119
+ return t
120
+ def t_START_TEXT(t):
121
+ r'"'
122
+ PRINT(t.value)
123
+ t.lexer.push_state("text")
124
+ def t_SYMBOL(t):
125
+ r'[a-zA-Z][a-zA-Z0-9_()\,]*'
126
+ PRINT(t.value)
127
+ return t
128
+
129
+ def t_text_TEXT(t):
130
+ r'([^"\]|\"|\)+'
131
+ PRINT(t.value)
132
+ return t
133
+ def t_text_END_TEXT(t):
134
+ r'"'
135
+ PRINT(t.value)
136
+ t.lexer.pop_state()
137
+
138
+ def t_version_VERSION(t):
139
+ r'[^;]+'
140
+ PRINT(t.value)
141
+ return t
142
+ def t_version_END_VERSION(t):
143
+ r';'
144
+ PRINT(t.value)
145
+ t.lexer.pop_state()
146
+ t.type = ';'
147
+ t.value = ';'
148
+ return t
149
+
150
+ #---------------------------------------------------------------------
151
+ # define error function
152
+ def t_ANY_error(t):
153
+ print("不正な文字 '%s'" % t.value[0])
154
+ print(t.lineno)
155
+ t.lexer.skip(1)
156
+
157
+ #---------------------------------------------------------------------
158
+ # declare instance
159
+ lex.lex(debug=0)
160
+
161
+ #---------------------------------------------------------------------
162
+ # main process
163
+
164
+ # debug main
165
+ def debug_main():
166
+ #data = open('test.txt').read()
167
+ data = input()
168
+ lex.input(data)
169
+ while(True):
170
+ tok = lex.token()
171
+ if not tok:
172
+ break
173
+
174
+ # debug entry point
175
+ if __name__ == "__main__":
176
+ debug_main()
177
+
178
+ ```
179
+
180
+ ```python
181
+ #!/usr/bin/env python
182
+ from ...ExImports import *
183
+ import ply.yacc as yacc
184
+ from .lex import tokens
185
+ from ..Common import *
186
+
187
+ def p_input(p):
188
+ 'input : EBGUIDE VERSION ";" file_root'
189
+ p[0] = p[4]
190
+
191
+ def p_flie_root(p):
192
+ 'file_root : OBJ_ID object'
193
+ p[0] = p[1]
194
+
195
+ def p_object(p):
196
+ 'object : "{" properties "}"'
197
+ p[0] = p[2]
198
+
199
+ def p_properties(p):
200
+ '''properties :
201
+ | properties simple_property
202
+ | properties data_binded_property
203
+ | properties nest_property'''
204
+ if (len(p) == 1):
205
+ p[0] = []
206
+ return
207
+ p[0] = p[1]
208
+ p[0].append(p[2])
209
+
210
+ def p_simple_property(p):
211
+ ''' simple_property : PROP_ID SYMBOL SYMBOL text ";"
212
+ | PROP_ID SYMBOL SYMBOL NUMBER ";"
213
+ | PROP_ID SYMBOL SYMBOL BOOL ";"
214
+ | PROP_ID text SYMBOL text ";"
215
+ | PROP_ID text SYMBOL NUMBER ";"
216
+ | PROP_ID text SYMBOL BOOL ";" '''
217
+ p[0] = p[1]
218
+ SimpleProperty(p[1], p[2], p[3], p[4])
219
+
220
+ def p_data_binded_property(p):
221
+ ''' data_binded_property : PROP_ID text SYMBOL prop_id ";" '''
222
+ p[0] = p[1]
223
+ SimpleProperty(p[1], p[2], p[3], p[4])
224
+
225
+ def p_nest_property(p):
226
+ ''' nest_property : PROP_ID SYMBOL SYMBOL OBJ_ID object
227
+ | PROP_ID SYMBOL SYMBOL array ";"
228
+ | PROP_ID text SYMBOL OBJ_ID ";"
229
+ | PROP_ID text SYMBOL OBJ_ID object
230
+ | PROP_ID text SYMBOL array ";"'''
231
+ p[0] = p[1]
232
+ SimpleProperty(p[1], p[2], p[3], p[4])
233
+
234
+ def p_text(p):
235
+ '''text :
236
+ | TEXT'''
237
+ p[0] = reduce(lambda x, y: x + y, p[1:], "")
238
+
239
+ def p_prop_id(p):
240
+ '''prop_id : PROP_ID
241
+ | OBJ_ID PROP_ID'''
242
+ p[0] = reduce(lambda x, y: x + y, p[1:], "")
243
+
244
+ def p_array(p):
245
+ '''array : array_header "[" "]"
246
+ | array_header "[" obj_array "]"
247
+ | array_header "[" int_array "]"
248
+ | array_header "[" text_array "]"
249
+ | array_header "[" obj_ref_array "]"
250
+ | array_header "[" prop_ref_array "]"'''
251
+ p[0] = p[4] if len(p) != 4 else []
252
+
253
+ def p_array_header(p):
254
+ 'array_header : "<" SYMBOL ">"'
255
+
256
+ def p_obj_array(p):
257
+ '''obj_array : nameless_obj
258
+ | obj_array "," nameless_obj'''
259
+ p[0] = [] if len(p) == 2 else p[1]
260
+ p[0].append(p[-1])
261
+
262
+ def p_int_array(p):
263
+ '''int_array : NUMBER
264
+ | int_array "," NUMBER'''
265
+ p[0] = [] if len(p) == 2 else p[1]
266
+ p[0].append(p[-1])
267
+
268
+ def p_text_array(p):
269
+ '''text_array : TEXT
270
+ | text_array "," TEXT'''
271
+ p[0] = [] if len(p) == 2 else p[1]
272
+ p[0].append(p[-1])
273
+
274
+ def p_obj_ref_array(p):
275
+ '''obj_ref_array : OBJ_ID
276
+ | obj_ref_array "," OBJ_ID'''
277
+ p[0] = [] if len(p) == 2 else p[1]
278
+ p[0].append(p[-1])
279
+
280
+ def p_prop_ref_array(p):
281
+ '''prop_ref_array : prop_id
282
+ | prop_ref_array "," prop_id '''
283
+ p[0] = [] if len(p) == 2 else p[1]
284
+ p[0].append(p[-1])
285
+
286
+ def p_nameless_obj(p):
287
+ 'nameless_obj : SYMBOL OBJ_ID object'
288
+ p[0] = p[3]
289
+
290
+ # syntax error
291
+ def p_error(p):
292
+ print ('Syntax error in input %s' %p)
293
+
294
+ parser = yacc.yacc()
295
+
296
+ # Debug
297
+ def parse(data, debug=0):
298
+ return yacc.parse(data, debug=debug)
299
+
300
+ if __name__ == '__main__':
301
+ data = open('test.txt').read()
302
+ result = parser.parse(data)
303
+ ```