improve loop checks
1 |
function is_func_call(x::EXPR) |
|
2 | 23 |
if typof(x) === Call |
3 | 23 |
return true |
4 | 23 |
elseif iswherecall(x) |
5 | 23 |
return is_func_call(x.args[1]) |
6 | 23 |
elseif isbracketed(x) |
7 | 23 |
return is_func_call(x.args[2]) |
8 | 23 |
elseif isunarycall(x) |
9 | 23 |
return !(isoperator(x.args[1]) && (kindof(x.args[1]) === Tokens.EX_OR || kindof(x.args[1]) === Tokens.DECLARATION)) |
10 | 23 |
elseif isbinarycall(x) |
11 | 23 |
if issyntaxcall(x.args[2]) |
12 | 23 |
if is_decl(x.args[2]) |
13 | 23 |
return is_func_call(x.args[1]) |
14 |
else
|
|
15 | 23 |
return false |
16 |
end
|
|
17 |
else
|
|
18 | 23 |
true
|
19 |
end
|
|
20 |
else
|
|
21 | 23 |
return false |
22 |
end
|
|
23 |
end
|
|
24 |
|
|
25 | 23 |
is_assignment(x) = isbinarycall(x) && kindof(x.args[2]) === Tokens.EQ |
26 |
|
|
27 |
# OPERATOR
|
|
28 | 23 |
is_exor(x) = isoperator(x) && kindof(x) === Tokens.EX_OR && x.dot == false |
29 | 23 |
is_decl(x) = isoperator(x) && kindof(x) === Tokens.DECLARATION |
30 | 23 |
is_issubt(x) = isoperator(x) && kindof(x) === Tokens.ISSUBTYPE |
31 | 23 |
is_issupt(x) = isoperator(x) && kindof(x) === Tokens.ISSUPERTYPE |
32 | 23 |
is_and(x) = isoperator(x) && kindof(x) === Tokens.AND && x.dot == false |
33 | 23 |
is_not(x) = isoperator(x) && kindof(x) === Tokens.NOT && x.dot == false |
34 | 23 |
is_plus(x) = isoperator(x) && kindof(x) === Tokens.PLUS && x.dot == false |
35 | 23 |
is_minus(x) = isoperator(x) && kindof(x) === Tokens.MINUS && x.dot == false |
36 | 23 |
is_star(x) = isoperator(x) && kindof(x) === Tokens.STAR && x.dot == false |
37 | 23 |
is_eq(x) = isoperator(x) && kindof(x) === Tokens.EQ && x.dot == false |
38 | 23 |
is_dot(x) = isoperator(x) && kindof(x) === Tokens.DOT |
39 | 23 |
is_ddot(x) = isoperator(x) && kindof(x) === Tokens.DDOT |
40 | 23 |
is_dddot(x) = isoperator(x) && kindof(x) === Tokens.DDDOT |
41 | 23 |
is_pairarrow(x) = isoperator(x) && kindof(x) === Tokens.PAIR_ARROW && x.dot == false |
42 | 23 |
is_in(x) = isoperator(x) && kindof(x) === Tokens.IN && x.dot == false |
43 | 23 |
is_elof(x) = isoperator(x) && kindof(x) === Tokens.ELEMENT_OF && x.dot == false |
44 | 23 |
is_colon(x) = isoperator(x) && kindof(x) === Tokens.COLON |
45 | 23 |
is_prime(x) = isoperator(x) && kindof(x) === Tokens.PRIME |
46 | 23 |
is_cond(x) = isoperator(x) && kindof(x) === Tokens.CONDITIONAL |
47 | 23 |
is_where(x) = isoperator(x) && kindof(x) === Tokens.WHERE |
48 | 23 |
is_anon_func(x) = isoperator(x) && kindof(x) === Tokens.ANON_FUNC |
49 |
|
|
50 | 23 |
is_comma(x) = ispunctuation(x) && kindof(x) === Tokens.COMMA |
51 | 23 |
is_lparen(x) = ispunctuation(x) && kindof(x) === Tokens.LPAREN |
52 |
is_rparen(x) = ispunctuation(x) && kindof(x) === Tokens.RPAREN |
|
53 |
is_lbrace(x) = ispunctuation(x) && kindof(x) === Tokens.LBRACE |
|
54 |
is_rbrace(x) = ispunctuation(x) && kindof(x) === Tokens.RBRACE |
|
55 |
is_lsquare(x) = ispunctuation(x) && kindof(x) === Tokens.LSQUARE |
|
56 |
is_rsquare(x) = ispunctuation(x) && kindof(x) === Tokens.RSQUARE |
|
57 |
|
|
58 |
# KEYWORD
|
|
59 | 23 |
is_if(x) = iskw(x) && kindof(x) === Tokens.IF |
60 | 23 |
is_import(x) = iskw(x) && kindof(x) === Tokens.IMPORT |
61 |
|
|
62 |
|
|
63 |
# Literals
|
|
64 |
is_lit_string(x) = kindof(x) === Tokens.STRING || kindof(x) === Tokens.TRIPLE_STRING |
|
65 |
|
|
66 | 23 |
issubtypedecl(x::EXPR) = isbinarycall(x) && is_issubt(x.args[2]) |
67 |
|
|
68 | 23 |
rem_subtype(x::EXPR) = issubtypedecl(x) ? x[1] : x |
69 | 23 |
rem_decl(x::EXPR) = isdeclaration(x) ? x[1] : x |
70 | 23 |
rem_curly(x::EXPR) = typof(x) === Curly ? x.args[1] : x |
71 | 23 |
rem_call(x::EXPR) = typof(x) === Call ? x[1] : x |
72 |
rem_where(x::EXPR) = iswherecall(x) ? x[1] : x |
|
73 | 23 |
rem_wheres(x::EXPR) = iswherecall(x) ? rem_wheres(x[1]) : x |
74 |
rem_where_subtype(x::EXPR) = (iswherecall(x) || issubtypedecl(x)) ? x[1] : x |
|
75 |
rem_where_decl(x::EXPR) = (iswherecall(x) || isdeclaration(x)) ? x[1] : x |
|
76 | 23 |
rem_invis(x::EXPR) = isbracketed(x) ? rem_invis(x[2]) : x |
77 |
rem_dddot(x::EXPR) = is_splat(x) ? x[1] : x |
|
78 |
const rem_splat = rem_dddot |
|
79 |
rem_kw(x::EXPR) = typof(x) === Kw ? x[1] : x |
|
80 |
|
|
81 | 23 |
is_some_call(x) = typof(x) === Call || isunarycall(x) || (isbinarycall(x) && !(kindof(x.args[2]) === Tokens.DOT || issyntaxcall(x.args[2]))) |
82 | 23 |
is_eventually_some_call(x) = is_some_call(x) || ((isdeclaration(x) || iswherecall(x)) && is_eventually_some_call(x[1])) |
83 |
|
|
84 | 23 |
defines_function(x::EXPR) = typof(x) === FunctionDef || (is_assignment(x) && is_eventually_some_call(x[1])) |
85 |
defines_macro(x) = typof(x) == Macro |
|
86 |
defines_datatype(x) = defines_struct(x) || defines_abstract(x) || defines_primitive(x) |
|
87 | 23 |
defines_struct(x) = typof(x) === Struct || defines_mutable(x) |
88 | 23 |
defines_mutable(x) = typof(x) === Mutable |
89 | 23 |
defines_abstract(x) = typof(x) === Abstract |
90 | 23 |
defines_primitive(x) = typof(x) === Primitive |
91 |
defines_module(x) = typof(x) === ModuleH || typof(x) === BareModule |
|
92 |
defines_anon_function(x) = isbinarycall(x) && is_anon_func(x.args[2]) |
|
93 |
|
|
94 |
has_sig(x::EXPR) = defines_datatype(x) || defines_function(x) || defines_macro(x) || defines_anon_function(x) |
|
95 |
|
|
96 |
"""
|
|
97 |
get_sig(x)
|
|
98 |
|
|
99 |
Returns the full signature of function, macro and datatype definitions.
|
|
100 |
Should only be called when has_sig(x) == true.
|
|
101 |
"""
|
|
102 |
function get_sig(x::EXPR) |
|
103 | 23 |
if isbinarycall(x) |
104 |
return x.args[1] |
|
105 | 23 |
elseif typof(x) === Struct || typof(x) === FunctionDef || typof(x) === Macro |
106 | 23 |
return x.args[2] |
107 | 23 |
elseif typof(x) === Mutable || typof(x) === Abstract || typof(x) === Primitive |
108 | 23 |
return x.args[3] |
109 |
end
|
|
110 |
end
|
|
111 |
|
|
112 |
function get_name(x::EXPR) |
|
113 | 23 |
if typof(x) === Struct || typof(x) === Mutable || typof(x) === Abstract || typof(x) === Primitive |
114 | 23 |
sig = get_sig(x) |
115 | 23 |
sig = rem_subtype(sig) |
116 | 23 |
sig = rem_wheres(sig) |
117 | 23 |
sig = rem_subtype(sig) |
118 | 23 |
sig = rem_curly(sig) |
119 | 23 |
elseif typof(x) === ModuleH || typof(x) === BareModule |
120 |
sig = x.args[2] |
|
121 | 23 |
elseif typof(x) === FunctionDef || typof(x) === Macro |
122 | 23 |
sig = get_sig(x) |
123 | 23 |
sig = rem_wheres(sig) |
124 | 23 |
sig = rem_decl(sig) |
125 | 23 |
sig = rem_call(sig) |
126 | 23 |
sig = rem_curly(sig) |
127 | 23 |
sig = rem_invis(sig) |
128 | 23 |
if isbinarycall(sig) && kindof(sig.args[2]) === Tokens.DOT |
129 |
if length(sig.args) > 2 && sig.args[3].args isa Vector{EXPR} && length(sig.args[3].args) > 0 |
|
130 |
sig = sig.args[3].args[1] |
|
131 |
end
|
|
132 |
end
|
|
133 | 23 |
return sig |
134 | 23 |
elseif isbinarycall(x) |
135 | 23 |
length(x.args) < 2 && return x |
136 | 23 |
if kindof(x.args[2]) === Tokens.DOT |
137 |
if length(x.args) > 2 && typof(x.args[3]) === Quotenode && x.args[3].args isa Vector{EXPR} && length(x.args[3].args) > 0 |
|
138 |
return get_name(x.args[3].args[1]) |
|
139 |
else
|
|
140 |
return x |
|
141 |
end
|
|
142 |
end
|
|
143 | 23 |
sig = x.args[1] |
144 | 23 |
if isunarycall(sig) |
145 | 23 |
return get_name(sig.args[1]) |
146 |
end
|
|
147 | 23 |
sig = rem_wheres(sig) |
148 | 23 |
sig = rem_decl(sig) |
149 | 23 |
sig = rem_call(sig) |
150 | 23 |
sig = rem_curly(sig) |
151 | 23 |
sig = rem_invis(sig) |
152 | 23 |
return get_name(sig) |
153 |
else
|
|
154 | 4 |
sig = x |
155 | 23 |
if isunarycall(sig) |
156 |
sig = sig.args[1] |
|
157 |
end
|
|
158 | 23 |
sig = rem_wheres(sig) |
159 | 23 |
sig = rem_decl(sig) |
160 | 23 |
sig = rem_call(sig) |
161 | 23 |
sig = rem_curly(sig) |
162 | 23 |
sig = rem_invis(sig) |
163 |
end
|
|
164 |
end
|
|
165 |
|
|
166 |
function get_arg_name(arg::EXPR) |
|
167 |
arg = rem_kw(arg) |
|
168 |
arg = rem_dddot(arg) |
|
169 |
arg = rem_where(arg) |
|
170 |
arg = rem_decl(arg) |
|
171 |
arg = rem_subtype(arg) |
|
172 |
arg = rem_curly(arg) |
|
173 |
arg = rem_invis(arg) |
|
174 |
end
|
Read our documentation on viewing source code .