9
9
namespace LCompilers {
10
10
11
11
/*
12
- This ASR pass replaces print list with print every value,
12
+ This ASR pass replaces print list or print tuple with print every value,
13
13
comma_space, brackets and newline. The function
14
14
`pass_replace_print_list` transforms the ASR tree in-place.
15
15
@@ -44,6 +44,22 @@ for nested lists it transforms to:
44
44
print("]", sep="pqr", end="xyz")
45
45
46
46
Note: In code, the variable `i` is named as `__list_iterator`
47
+
48
+ For tuples:
49
+
50
+ Converts:
51
+ a: tuple[i32, str, f32] = (10, 'lpython', 24.04)
52
+ print(a, sep="pqr", end="xyz")
53
+
54
+ to:
55
+ print("(", end="")
56
+ for i in range(3):
57
+ print(a[i], end="")
58
+ if i < len(a) - 1:
59
+ print(", ", end="")
60
+ print(")", sep="pqr", end="xyz")
61
+
62
+ It also works the same way for nested lists/tuples using recursion.
47
63
*/
48
64
49
65
class PrintListVisitor
@@ -163,14 +179,17 @@ class PrintListVisitor
163
179
loop_head.m_increment =
164
180
ASRUtils::EXPR (ASR::make_IntegerConstant_t (
165
181
al, loc, 1 , int_type));
166
-
167
- if (!ASR::is_a<ASR::List_t>(*listC->m_type )) {
168
- loop_body.reserve (al, 2 );
169
- loop_body.push_back (al, print_item);
170
- } else {
182
+ if (ASR::is_a<ASR::List_t>(*listC->m_type )){
171
183
print_list_helper (list_item, nullptr , empty_str, loc);
172
184
loop_body.from_pointer_n_copy (al, print_pass_result_tmp.p , print_pass_result_tmp.size ());
173
185
print_pass_result_tmp.n = 0 ;
186
+ } else if (ASR::is_a<ASR::Tuple_t>(*listC->m_type )) {
187
+ print_tuple_helper (list_item, nullptr , empty_str, loc);
188
+ loop_body.from_pointer_n_copy (al, print_pass_result_tmp.p , print_pass_result_tmp.size ());
189
+ print_pass_result_tmp.n = 0 ;
190
+ } else {
191
+ loop_body.reserve (al, 2 );
192
+ loop_body.push_back (al, print_item);
174
193
}
175
194
loop_body.push_back (al, if_cond);
176
195
}
@@ -185,10 +204,104 @@ class PrintListVisitor
185
204
}
186
205
}
187
206
207
+ void print_tuple_helper (ASR::expr_t *tup_expr, ASR::expr_t *sep_expr,
208
+ ASR::expr_t *end_expr, const Location &loc) {
209
+ ASR::Tuple_t *tup =
210
+ ASR::down_cast<ASR::Tuple_t>(ASRUtils::expr_type (tup_expr));
211
+ ASR::ttype_t *int_type = ASRUtils::TYPE (
212
+ ASR::make_Integer_t (al, loc, 4 , nullptr , 0 ));
213
+ ASR::ttype_t *str_type_len_0 = ASRUtils::TYPE (ASR::make_Character_t (
214
+ al, loc, 1 , 0 , nullptr , nullptr , 0 ));
215
+ ASR::ttype_t *str_type_len_1 = ASRUtils::TYPE (ASR::make_Character_t (
216
+ al, loc, 1 , 1 , nullptr , nullptr , 0 ));
217
+ ASR::ttype_t *str_type_len_2 = ASRUtils::TYPE (ASR::make_Character_t (
218
+ al, loc, 1 , 2 , nullptr , nullptr , 0 ));
219
+ ASR::expr_t *comma_space =
220
+ ASRUtils::EXPR (ASR::make_StringConstant_t (
221
+ al, loc, s2c (al, " , " ), str_type_len_2));
222
+ ASR::expr_t *single_quote =
223
+ ASRUtils::EXPR (ASR::make_StringConstant_t (
224
+ al, loc, s2c (al, " '" ), str_type_len_1));
225
+ ASR::expr_t *empty_str = ASRUtils::EXPR (ASR::make_StringConstant_t (
226
+ al, loc, s2c (al, " " ), str_type_len_0));
227
+ ASR::expr_t *open_bracket =
228
+ ASRUtils::EXPR (ASR::make_StringConstant_t (
229
+ al, loc, s2c (al, " (" ), str_type_len_1));
230
+ ASR::expr_t *close_bracket =
231
+ ASRUtils::EXPR (ASR::make_StringConstant_t (
232
+ al, loc, s2c (al, " )" ), str_type_len_1));
233
+
234
+ std::string tup_iter_var_name;
235
+ ASR::expr_t *tup_iter_var, *tup_item;
236
+ Vec<ASR::expr_t *> v1, v3, v4;
237
+ v1.reserve (al, 1 );
238
+ v3.reserve (al, 1 );
239
+ v4.reserve (al, 1 );
240
+ v1.push_back (al, open_bracket);
241
+ v3.push_back (al, close_bracket);
242
+ v4.push_back (al, comma_space);
243
+
244
+ Vec<ASR::stmt_t *> tmp_vec;
245
+ tmp_vec.reserve (al, 3 );
246
+ ASR::stmt_t *print_open_bracket = ASRUtils::STMT (
247
+ ASR::make_Print_t (al, loc, nullptr , v1.p , v1.size (),
248
+ nullptr , empty_str));
249
+ ASR::stmt_t *print_comma_space = ASRUtils::STMT (
250
+ ASR::make_Print_t (al, loc, nullptr , v4.p , v4.size (),
251
+ empty_str, empty_str));
252
+ ASR::stmt_t *print_close_bracket = ASRUtils::STMT (
253
+ ASR::make_Print_t (al, loc, nullptr , v3.p , v3.size (),
254
+ sep_expr, end_expr));
255
+
256
+ tmp_vec.push_back (al, print_open_bracket);
257
+ for (size_t i=0 ; i<tup->n_type ; i++) {
258
+ tup_iter_var = ASRUtils::EXPR (
259
+ ASR::make_IntegerConstant_t (al, loc, i, int_type));
260
+ tup_item = ASRUtils::EXPR (ASR::make_TupleItem_t (al, loc, tup_expr,
261
+ tup_iter_var, tup->m_type [i], nullptr ));
262
+ if (ASR::is_a<ASR::List_t>(*tup->m_type [i])) {
263
+ print_pass_result_tmp.n = 0 ;
264
+ print_list_helper (tup_item, nullptr , empty_str, loc);
265
+ for (size_t j=0 ; j<print_pass_result_tmp.n ; j++) {
266
+ tmp_vec.push_back (al, print_pass_result_tmp[j]);
267
+ }
268
+ print_pass_result_tmp.n = 0 ;
269
+ } else if (ASR::is_a<ASR::Tuple_t>(*tup->m_type [i])) {
270
+ print_pass_result_tmp.n = 0 ;
271
+ print_tuple_helper (tup_item, nullptr , empty_str, loc);
272
+ for (size_t j=0 ; j<print_pass_result_tmp.n ; j++) {
273
+ tmp_vec.push_back (al, print_pass_result_tmp[j]);
274
+ }
275
+ print_pass_result_tmp.n = 0 ;
276
+ } else {
277
+ Vec<ASR::expr_t *> v2;
278
+ if (ASR::is_a<ASR::Character_t>(*tup->m_type [i])) {
279
+ v2.reserve (al, 3 );
280
+ v2.push_back (al, single_quote);
281
+ v2.push_back (al, tup_item);
282
+ v2.push_back (al, single_quote);
283
+ } else {
284
+ v2.reserve (al, 1 );
285
+ v2.push_back (al, tup_item);
286
+ }
287
+ ASR::stmt_t *print_item = ASRUtils::STMT (
288
+ ASR::make_Print_t (al, loc, nullptr , v2.p , v2.size (),
289
+ empty_str, empty_str));
290
+ tmp_vec.push_back (al, print_item);
291
+ }
292
+ if (i != tup->n_type - 1 ) {
293
+ tmp_vec.push_back (al, print_comma_space);
294
+ }
295
+ }
296
+ tmp_vec.push_back (al, print_close_bracket);
297
+ print_pass_result_tmp.from_pointer_n_copy (al, tmp_vec.p , tmp_vec.size ());
298
+ }
299
+
188
300
void visit_Print (const ASR::Print_t &x) {
189
301
std::vector<ASR::expr_t *> print_tmp;
190
302
for (size_t i=0 ; i<x.n_values ; i++) {
191
- if (ASR::is_a<ASR::List_t>(*ASRUtils::expr_type (x.m_values [i]))) {
303
+ if (ASR::is_a<ASR::List_t>(*ASRUtils::expr_type (x.m_values [i])) ||
304
+ ASR::is_a<ASR::Tuple_t>(*ASRUtils::expr_type (x.m_values [i]))) {
192
305
if (!print_tmp.empty ()) {
193
306
Vec<ASR::expr_t *> tmp_vec;
194
307
tmp_vec.reserve (al, print_tmp.size ());
@@ -202,7 +315,10 @@ class PrintListVisitor
202
315
pass_result.push_back (al, print_stmt);
203
316
204
317
}
205
- print_list_helper (x.m_values [i], x.m_separator , nullptr , x.base .base .loc );
318
+ if (ASR::is_a<ASR::List_t>(*ASRUtils::expr_type (x.m_values [i])))
319
+ print_list_helper (x.m_values [i], x.m_separator , nullptr , x.base .base .loc );
320
+ else
321
+ print_tuple_helper (x.m_values [i], x.m_separator , nullptr , x.base .base .loc );
206
322
for (size_t j=0 ; j<print_pass_result_tmp.n ; j++)
207
323
pass_result.push_back (al, print_pass_result_tmp[j]);
208
324
print_pass_result_tmp.n = 0 ;
0 commit comments