Skip to content

Commit 402a7bb

Browse files
committed
⚡ Use frozen const when parsing empty arrays [🚧 WIP]
TODO, record benchmarks
1 parent 45c6628 commit 402a7bb

File tree

1 file changed

+17
-9
lines changed

1 file changed

+17
-9
lines changed

lib/net/imap/response_parser.rb

Lines changed: 17 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,10 @@ def parse(str)
6262
T_TEXT = :TEXT # any char except CRLF
6363
T_EOF = :EOF # end of response string
6464

65+
# Use to avoid allocation when we know the result is empty
66+
EMPTY_ARRAY = [].freeze
67+
private_constant :EMPTY_ARRAY
68+
6569
module ResponseConditions
6670
OK = "OK"
6771
NO = "NO"
@@ -614,7 +618,7 @@ def tagged_ext_simple
614618
# "(" [tagged-ext-comp] ")"
615619
def tagged_ext_val
616620
if lpar?
617-
_ = peek_rpar? ? [] : tagged_ext_comp
621+
_ = peek_rpar? ? EMPTY_ARRAY : tagged_ext_comp
618622
rpar
619623
_
620624
else
@@ -1386,7 +1390,7 @@ def mailbox_data__list
13861390
# ; This is the list information pointed to by the ABNF
13871391
# ; item "mailbox-data", which is defined above
13881392
def mailbox_list
1389-
lpar; attr = peek_rpar? ? [] : mbx_list_flags; rpar
1393+
lpar; attr = peek_rpar? ? EMPTY_ARRAY : mbx_list_flags; rpar
13901394
SP!; delim = nquoted
13911395
SP!; name = mailbox
13921396
# TODO: mbox-list-extended
@@ -1486,8 +1490,12 @@ def acl_data
14861490
# obsolete-search-response = "SEARCH" *(SP nz-number)
14871491
def mailbox_data__search
14881492
name = label_in("SEARCH", "SORT")
1489-
data = []
1490-
while _ = SP? && nz_number? do data << _ end
1493+
if (_ = SP? && nz_number?)
1494+
data = [_]
1495+
while _ = SP? && nz_number? do data << _ end
1496+
else
1497+
data = EMPTY_ARRAY
1498+
end
14911499
if lpar?
14921500
label("MODSEQ"); SP!
14931501
modseq = mod_sequence_value
@@ -1641,7 +1649,7 @@ def thread_members
16411649
else nested = thread_nested; break
16421650
end
16431651
end
1644-
members.reverse.inject(nested || []) {|subthreads, number|
1652+
members.reverse.inject(nested || EMPTY_ARRAY) {|subthreads, number|
16451653
[ThreadMember.new(number, subthreads)]
16461654
}.first
16471655
end
@@ -1813,7 +1821,7 @@ def namespace_response
18131821

18141822
# namespace = nil / "(" 1*namespace-descr ")"
18151823
def namespace
1816-
NIL? and return []
1824+
NIL? and return EMPTY_ARRAY
18171825
lpar
18181826
list = [namespace_descr]
18191827
list << namespace_descr until rpar?
@@ -1940,13 +1948,13 @@ def resp_text_code
19401948
data =
19411949
case name
19421950
when "CAPABILITY" then resp_code__capability
1943-
when "PERMANENTFLAGS" then SP? ? flag_perm__list : []
1951+
when "PERMANENTFLAGS" then SP? ? flag_perm__list : EMPTY_ARRAY
19441952
when "UIDNEXT" then SP!; nz_number
19451953
when "UIDVALIDITY" then SP!; nz_number
19461954
when "UNSEEN" then SP!; nz_number # rev1 only
19471955
when "APPENDUID" then SP!; resp_code_apnd__data # rev2, UIDPLUS
19481956
when "COPYUID" then SP!; resp_code_copy__data # rev2, UIDPLUS
1949-
when "BADCHARSET" then SP? ? charset__list : []
1957+
when "BADCHARSET" then SP? ? charset__list : EMPTY_ARRAY
19501958
when "ALERT", "PARSE", "READ-ONLY", "READ-WRITE", "TRYCREATE",
19511959
"UNAVAILABLE", "AUTHENTICATIONFAILED", "AUTHORIZATIONFAILED",
19521960
"EXPIRED", "PRIVACYREQUIRED", "CONTACTADMIN", "NOPERM", "INUSE",
@@ -2077,7 +2085,7 @@ def x_gm_label; accept(T_BSLASH) ? atom.capitalize.to_sym : astring end
20772085

20782086
# See https://developers.google.com/gmail/imap/imap-extensions
20792087
def x_gm_labels
2080-
lpar; return [] if rpar?
2088+
lpar; return EMPTY_ARRAY if rpar?
20812089
labels = []
20822090
labels << x_gm_label
20832091
labels << x_gm_label while SP?

0 commit comments

Comments
 (0)