at_coder_friends 0.6.2 → 0.6.3

Sign up to get free protection for your applications and to get access to all the features.
@@ -3,43 +3,20 @@
3
3
  module AtCoderFriends
4
4
  module Generator
5
5
  # generates Ruby source from problem description
6
- class RubyBuiltin
6
+ class RubyBuiltin < Base
7
7
  ACF_HOME = File.realpath(File.join(__dir__, '..', '..', '..'))
8
8
  TMPL_DIR = File.join(ACF_HOME, 'templates')
9
- DEFAULT_TMPL = File.join(TMPL_DIR, 'ruby_builtin_default.rb')
10
- INTERACTIVE_TMPL = File.join(TMPL_DIR, 'ruby_builtin_interactive.rb')
9
+ DEFAULT_TMPL = File.join(TMPL_DIR, 'ruby_builtin.rb.erb')
10
+ ATTRS = Attributes.new(:rb, DEFAULT_TMPL)
11
11
 
12
- attr_reader :cfg, :pbm
13
-
14
- def initialize(cfg = nil)
15
- @cfg = cfg || {}
16
- end
17
-
18
- def process(pbm)
19
- src = generate(pbm)
20
- pbm.add_src(:rb, src)
21
- end
22
-
23
- def generate(pbm)
24
- @pbm = pbm
25
- File
26
- .read(select_template)
27
- .gsub('### URL ###', pbm.url)
28
- .gsub('### CONSTS ###', gen_consts.join("\n"))
29
- .gsub('### DCLS ###', gen_decls.join("\n"))
30
- .gsub('### OUTPUT ###', gen_output)
12
+ def attrs
13
+ ATTRS
31
14
  end
32
15
 
33
- def select_template(interactive = pbm.options.interactive)
34
- interactive ? interactive_template : default_template
35
- end
36
-
37
- def default_template
38
- cfg['default_template'] || DEFAULT_TMPL
39
- end
40
-
41
- def interactive_template
42
- cfg['interactive_template'] || INTERACTIVE_TMPL
16
+ def render(src)
17
+ src = embed_lines(src, '### CONSTS ###', gen_consts)
18
+ src = embed_lines(src, '### DCLS ###', gen_decls)
19
+ src
43
20
  end
44
21
 
45
22
  def gen_consts(constants = pbm.constants)
@@ -64,35 +41,45 @@ module AtCoderFriends
64
41
  when :harray
65
42
  gen_harray_decl(inpdef)
66
43
  when :varray
67
- if inpdef.names.size == 1
68
- gen_varray_1_decl(inpdef)
69
- else
70
- gen_varray_n_decl(inpdef)
71
- end
44
+ gen_varray_decl(inpdef)
72
45
  when :matrix
73
46
  gen_matrix_decl(inpdef)
47
+ when :varray_matrix, :matrix_varray
48
+ gen_cmb_decl(inpdef)
49
+ when :vmatrix
50
+ gen_vmatrix_decl(inpdef)
51
+ when :hmatrix
52
+ gen_hmatrix_decl(inpdef)
74
53
  end
75
54
  end
76
55
 
77
56
  def gen_single_decl(inpdef)
78
57
  names = inpdef.names
79
58
  dcl = names.join(', ')
80
- expr = gen_expr(inpdef.item, names.size > 1)
59
+ expr = gen_expr(inpdef, names.size > 1)
81
60
  "#{dcl} = #{expr}"
82
61
  end
83
62
 
84
63
  def gen_harray_decl(inpdef)
85
64
  v = inpdef.names[0]
86
65
  dcl = "#{v}s"
87
- expr = gen_expr(inpdef.item, true)
66
+ expr = gen_expr(inpdef, true)
88
67
  "#{dcl} = #{expr}"
89
68
  end
90
69
 
70
+ def gen_varray_decl(inpdef)
71
+ if inpdef.names.size == 1
72
+ gen_varray_1_decl(inpdef)
73
+ else
74
+ gen_varray_n_decl(inpdef)
75
+ end
76
+ end
77
+
91
78
  def gen_varray_1_decl(inpdef)
92
79
  v = inpdef.names[0]
93
80
  sz = inpdef.size[0]
94
81
  dcl = "#{v}s"
95
- expr = gen_expr(inpdef.item, false)
82
+ expr = gen_expr(inpdef, false)
96
83
  "#{dcl} = Array.new(#{sz}) { #{expr} }"
97
84
  end
98
85
 
@@ -100,7 +87,7 @@ module AtCoderFriends
100
87
  names = inpdef.names
101
88
  sz = inpdef.size[0]
102
89
  dcl = names.map { |v| "#{v}s[i]" }.join(', ')
103
- expr = gen_expr(inpdef.item, true)
90
+ expr = gen_expr(inpdef, true)
104
91
  ret = []
105
92
  ret += names.map { |v| "#{v}s = Array.new(#{sz})" }
106
93
  ret << "#{sz}.times do |i|"
@@ -113,28 +100,87 @@ module AtCoderFriends
113
100
  v = inpdef.names[0]
114
101
  sz = inpdef.size[0]
115
102
  decl = "#{v}ss"
116
- expr = gen_expr(inpdef.item, true)
103
+ expr = gen_expr(inpdef, true)
117
104
  "#{decl} = Array.new(#{sz}) { #{expr} }"
118
105
  end
119
106
 
120
- def gen_expr(item, split)
121
- case item
107
+ def gen_cmb_decl(inpdef)
108
+ mx = inpdef.container == :varray_matrix ? -1 : 0
109
+ vs = inpdef.names.map { |v| "#{v}s" }
110
+ vs[mx] += 's'
111
+ sz = inpdef.size[0]
112
+ dcls = vs.map { |v| "#{v}[i]" }
113
+ dcls[mx] = '*' + dcls[mx] unless inpdef.item == :char
114
+ dcl = dcls.join(', ')
115
+ expr = gen_cmb_expr(inpdef)
116
+ ret = []
117
+ ret += vs.map { |v| "#{v} = Array.new(#{sz})" }
118
+ ret << "#{sz}.times do |i|"
119
+ ret << " #{dcl} = #{expr}"
120
+ ret << 'end'
121
+ ret
122
+ end
123
+
124
+ def gen_vmatrix_decl(inpdef)
125
+ names = inpdef.names
126
+ sz1, sz2 = inpdef.size
127
+ dcl = names.map { |v| "#{v}ss[i][j]" }.join(', ')
128
+ expr = gen_expr(inpdef, true)
129
+ ret = []
130
+ ret += names.map do |v|
131
+ "#{v}ss = Array.new(#{sz1}) { Array.new(#{sz2}) }"
132
+ end
133
+ ret << "#{sz1}.times do |i|"
134
+ ret << " #{sz2}.times do |j|"
135
+ ret << " #{dcl} = #{expr}"
136
+ ret << ' end'
137
+ ret << 'end'
138
+ ret
139
+ end
140
+
141
+ def gen_hmatrix_decl(inpdef)
142
+ names = inpdef.names
143
+ sz = inpdef.size[0]
144
+ dcl = names.map { |v| "#{v}ss[i]" }.join(', ')
145
+ expr = gen_expr(inpdef, true)
146
+ ret = []
147
+ ret += names.map { |v| "#{v}ss = Array.new(#{sz})" }
148
+ ret << "#{sz}.times do |i|"
149
+ ret << " #{dcl} = #{expr}.each_slice(#{names.size}).to_a.transpose"
150
+ ret << 'end'
151
+ ret
152
+ end
153
+
154
+ def gen_expr(inpdef, split)
155
+ read = gen_read(inpdef.delim)
156
+ case inpdef.item
122
157
  when :number
123
- split ? 'gets.split.map(&:to_i)' : 'gets.to_i'
158
+ split ? "#{read}.split.map(&:to_i)" : "#{read}.to_i"
159
+ when :decimal
160
+ split ? "#{read}.split.map(&:to_f)" : "#{read}.to_f"
124
161
  when :string
125
- split ? 'gets.chomp.split' : 'gets.chomp'
162
+ split ? "#{read}.chomp.split" : "#{read}.chomp"
126
163
  when :char
127
164
  'gets.chomp'
128
165
  end
129
166
  end
130
167
 
131
- def gen_output(vs = pbm.options.binary_values)
132
- if vs
133
- "puts cond ? '#{vs[0]}' : '#{vs[1]}'"
134
- else
135
- 'puts ans'
168
+ def gen_cmb_expr(inpdef)
169
+ read = gen_read(inpdef.delim)
170
+ case inpdef.item
171
+ when :number
172
+ "#{read}.split.map(&:to_i)"
173
+ when :decimal
174
+ "#{read}.split.map(&:to_f)"
175
+ when :string, :char
176
+ "#{read}.chomp.split"
136
177
  end
137
178
  end
179
+
180
+ def gen_read(delim)
181
+ sub = delim.chars.map { |d| ".gsub('#{d}', ' ')" }.join
182
+ "gets#{sub}"
183
+ end
138
184
  end
139
185
  end
140
186
  end