-
-
Notifications
You must be signed in to change notification settings - Fork 265
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
refactor and speed up _realName code #893
Conversation
This way we can edit it as regular Go code, with the help of an LSP, and we can also test and benchmark it.
│ new │ │ sec/op │ AbiRealName-8 1.026m ± 6% │ new │ │ B/s │ AbiRealName-8 351.6Ki ± 6% │ new │ │ B/op │ AbiRealName-8 5.363Ki ± 0% │ new │ │ allocs/op │ AbiRealName-8 19.00 ± 0%
│ old │ new │ │ sec/op │ sec/op vs base │ AbiRealName-8 1025.9µ ± 6% 707.1µ ± 1% -31.08% (p=0.001 n=7) │ old │ new │ │ B/s │ B/s vs base │ AbiRealName-8 351.6Ki ± 6% 517.6Ki ± 2% +47.22% (p=0.001 n=7) │ old │ new │ │ B/op │ B/op vs base │ AbiRealName-8 5.363Ki ± 0% 5.362Ki ± 0% ~ (p=0.178 n=7) │ old │ new │ │ allocs/op │ allocs/op vs base │ AbiRealName-8 19.00 ± 0% 19.00 ± 0% ~ (p=1.000 n=7) ¹
Iterating over a map is much more expensive than iterating over a slice, given how it needs to work out which keys are present in each bucket and then randomize the order in which to navigate the keys. None of this work needs to happen when iterating over a slice. A map would be nice if we were to actually do map lookups, but we don't. │ old │ new │ │ sec/op │ sec/op vs base │ AbiRealName-8 707.1µ ± 1% 196.7µ ± 1% -72.17% (p=0.001 n=7) │ old │ new │ │ B/s │ B/s vs base │ AbiRealName-8 517.6Ki ± 2% 1816.4Ki ± 1% +250.94% (p=0.001 n=7) │ old │ new │ │ B/op │ B/op vs base │ AbiRealName-8 5.362Ki ± 0% 5.359Ki ± 0% -0.05% (p=0.001 n=7) │ old │ new │ │ allocs/op │ allocs/op vs base │ AbiRealName-8 19.00 ± 0% 19.00 ± 0% ~ (p=1.000 n=7) ¹
This refactoring and benchmarking is ultimately for #892. But I was also curious how fast I could get the existing simple algorithm to be, before we jump to something fancy like that strings replacer. It turns out we could be about 5x as fast. |
This lets us only check names up to the remaining input string length. │ old │ new │ │ sec/op │ sec/op vs base │ AbiRealName-8 196.7µ ± 1% 172.3µ ± 1% -12.41% (p=0.001 n=7) │ old │ new │ │ B/s │ B/s vs base │ AbiRealName-8 1.774Mi ± 1% 2.022Mi ± 0% +13.98% (p=0.001 n=7) │ old │ new │ │ B/op │ B/op vs base │ AbiRealName-8 5.359Ki ± 0% 5.336Ki ± 0% -0.44% (p=0.001 n=7) │ old │ new │ │ allocs/op │ allocs/op vs base │ AbiRealName-8 19.00 ± 0% 18.00 ± 0% -5.26% (p=0.001 n=7)
Use the term "original name" rather than "real name" for the code as it is clearer that we mean the unobfuscated name. Update the comments at the top of the file to be clearer with the explanation of what kinds of inputs we can expect. While here, use fmt.Appendf to simplify the generation code a bit.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Like that the injected code now lives in a real go file.
As Paul Scheduikat points out, the loop already does not start if the length of name is less than minHashLength. │ old │ new │ │ sec/op │ sec/op vs base │ AbiOriginalNames-8 135.6µ ± 1% 135.5µ ± 0% ~ (p=1.000 n=7)
I didn't rebase/squash as that would cause me silly conflicts to resolve. It seems fine to do one more commit to explain the last minute simplification. |
(see commit messages - please do not squash)