TE
TechEcho
Home24h TopNewestBestAskShowJobs
GitHubTwitter
Home

TechEcho

A tech news platform built with Next.js, providing global tech news and discussions.

GitHubTwitter

Home

HomeNewestBestAskShowJobs

Resources

HackerNews APIOriginal HackerNewsNext.js

© 2025 TechEcho. All rights reserved.

A single character code change

115 pointsby nfrankelover 5 years ago

23 comments

gmfawcettover 5 years ago
Good lord, this long-winded writing style is maddening to read!<p>Here&#x27;s what he changed:<p>&gt; Set&lt;Thing&gt; aSet = new HashSet&lt;Thing&gt;();<p>to:<p>&gt; Set&lt;Thing&gt; aSet = new HashSet&lt;Thing&gt;(0);<p>His explanation:<p>&quot;Most of these sets were empty for the entirety of their life, but each one was consuming enough memory to hold the default number of entries. Huge numbers of these empty sets were created and together they consumed over half a gigabyte of memory. Over a third of our available heap.&quot;<p>I&#x27;m not sure he ever got around to explaining how it saved &quot;half a million dollars&quot;, though.
评论 #21938261 未加载
评论 #21937957 未加载
评论 #21937874 未加载
评论 #21938220 未加载
评论 #21938264 未加载
评论 #21938030 未加载
评论 #21944701 未加载
评论 #21938607 未加载
评论 #21937932 未加载
评论 #21937860 未加载
评论 #21939639 未加载
评论 #21937913 未加载
评论 #21939122 未加载
评论 #21937916 未加载
评论 #21950369 未加载
评论 #21938215 未加载
评论 #21937835 未加载
评论 #21943096 未加载
评论 #21938429 未加载
kinkrtyavimoodhover 5 years ago
There is a &#x27;pre&#x27; in &#x27;pre-mature&#x27; for a reason. If you don&#x27;t seek to optimize even when it is &#x27;mature&#x27;, you are not a good software engineer.<p>In this story, instead of doing meetings, why did no one fire up the profiler and actually try to figure out why the heap size was so big? If the senior architect&#x27;s first thought is to come up with an elaborate proposal even before they understand the memory and processing budgets of their program, what are they a senior architect for? It&#x27;s like trying to shave off micro seconds of processing time while your network call takes milliseconds.<p>Good style guides strike the balance where common caveats and easy to miss gotchas are avoided by making rules around them (and then it&#x27;s no longer premature optimization because someone already did the math and decided on the optimization, so each new programmer using it is not optimizing but merely following a rule in the style guide), while leaving the complex cases for the programmer to optimize as and when needed.<p>Many people who scoff at opinionated style guides forget that in a big company you don&#x27;t want 1000 engineers to spend time independently figuring out whether X needs to be optimized [1]. If someone can do the profiling, figure out what should be done in 99% of cases, make a style rule out of it explaining the rationale, it saves everyone the hassle. I believe Google does exactly this.<p>[1] Apart from the waste of time, not every engineer might be capable of actually figuring it out. Many of the intricacies of C++ for example aren&#x27;t immediately obvious even if you have spent years with the language. It&#x27;s more optimal to hire a few C++ super-experts, have them do the profiling, and come up with style guidance.
评论 #21938124 未加载
评论 #21939809 未加载
hinkleyover 5 years ago
Author discusses a Java 1.3 app where he saved tons of memory by reducing leaf collection sizes.<p>I had sort of the opposite with a Java 1.2 code base. Some clever person has noticed that a bunch of vectors often had only 4-7 entries so they overrode the default (10) to 7. This is unfortunately greater than n&#x2F;2 which will become important momentarily.<p>In Java collections tend to double in size on space exhaustion. Using a multiple instead of addition amortizes the insertion time to O(1). So if you start at 7, you go to 14 next.<p>As I’m sure you can guess, the number of entries crept up to 8 over time. Switching back to the defaults reduced the wasted space from 6 to 2 slots, and dropped our memory usage by more than 10%.
paulddraperover 5 years ago
I had a somewhat similar discovery with V8 (JS VM):<p>V8 allocates a whopping 64 bytes per empty object.<p><pre><code> {} </code></pre> But if you initialize it with a single property, the size <i>shrinks</i> to 40 bytes. [1]<p><pre><code> {v8Hack: null} </code></pre> I too was creating lots of object that would stay empty, but V8 (incorrectly) assumed I was going to change them later so it reserved some extra space. [2]<p>Unfortunately, there is no size hint like for Java&#x27;s HashMap; the closest hint you can do is create your objects with dummy properties.<p>[1] <a href="https:&#x2F;&#x2F;stackoverflow.com&#x2F;questions&#x2F;59044239&#x2F;why-do-empty-objects-take-more-memory-than-non-empty-ones" rel="nofollow">https:&#x2F;&#x2F;stackoverflow.com&#x2F;questions&#x2F;59044239&#x2F;why-do-empty-ob...</a><p>[2] <a href="https:&#x2F;&#x2F;www.mattzeunert.com&#x2F;2017&#x2F;03&#x2F;29&#x2F;v8-object-size.html" rel="nofollow">https:&#x2F;&#x2F;www.mattzeunert.com&#x2F;2017&#x2F;03&#x2F;29&#x2F;v8-object-size.html</a>
stygiansonicover 5 years ago
Although the article is a bit long-winded as others have pointed out, it did mention the importance of <i>profiling</i> your application before making any changes.<p>In particular, you should always aim to profile your app when running under a production load so that you do not have to make assumptions about its behaviour. Something like async-profiler[0] is good, since it avoids the safepoint bias issue and can also track heap allocations.<p>0. <a href="https:&#x2F;&#x2F;github.com&#x2F;jvm-profiling-tools&#x2F;async-profiler" rel="nofollow">https:&#x2F;&#x2F;github.com&#x2F;jvm-profiling-tools&#x2F;async-profiler</a>
bcrosby95over 5 years ago
Back in the 00&#x27;s our servers were suffering under heavy load. Normally they just bought more servers, but I asked if anyone ever profiled our app and no one could remember doing so. I did so and our home grown ORM did a couple really dumb things. Including access the disk each time it allocated a new object that represented a row (wtf). After spending a couple days fixing those things we needed 1&#x2F;4 of the servers we did beforehand.
redis_mlcover 5 years ago
Randal Schwartz saved more than that by enabling caching in a template for one of Yahoo&#x27;s properties near LA.<p>So it really is possible.<p>As a DBA, I routinely save that (and more) by doing query performance tuning. I aim for 500x-1,000x faster on physical hardware, and 10,000x in the cloud, thanks to EBS&#x2F;pSSD latency.<p>And not using Hadoop.
ping_pongover 5 years ago
Terrible article.<p>But even worse, the &quot;fix&quot; was what I would consider a spaghetti hack. They create a HashSet that is mostly never used? The real fix is to create the HashSet when you know you need it and don&#x27;t create it if you don&#x27;t need it. It sounds like the underlying code has expectations that the HashSet exists and is valid, which in and of itself is bad code.<p>Check to see if it&#x27;s null, and if it is null and you need it to not be null, then allocate it then, with size 0 or default capacity, whichever makes more sense.
评论 #21938335 未加载
mannykannotover 5 years ago
&gt; I had to spend time justifying the presence of that ‘0’ many times over the years as other developers questioned its purpose.<p>One of the better cases for using appropriate comments...
评论 #21938754 未加载
jandreseover 5 years ago
I have to wonder about an architecture where he&#x27;s creating thousands of these hash objects <i>and then rarely using them</i>. Initializing them to size 0 was a workaround, but it makes me wonder if maybe he should consider lazy evaluation where the objects are only created if they&#x27;re actually used? That&#x27;s still a bunch of CPU cycles burned churning through the setup&#x2F;teardown of empty hash tables.
评论 #21939614 未加载
评论 #21938718 未加载
enitihasover 5 years ago
If your java application needs a lot of small collections, it may make sense to use guava immutable collections. They have specialised overloads for lots of sizes, and small collections will not take any more memory than a hardcoded minimal collection.
ChrisMarshallNYover 5 years ago
It seems to mostly be about optimization.<p>There are some good points, but, like so many of these topics, it enters the world of &quot;orthodoxy,&quot; where we all have to do things the same way, everywhere, and in all places.<p>Optimization (effective optimization, anyway) is a fairly intense process. For one thing, common sense doesn&#x27;t really apply. What <i>seems</i> to be an optimization can sometimes do exactly the opposite, like breaking cache, or introducing thread contention.<p>It can also introduce <i>really weird</i> bugs, that are hard to track down, and strange code structures that relatively inexperienced maintenance programmers may have difficulty grokking.<p>It&#x27;s all about the metrics. Profilers are your friend.<p>Also, in many cases, optimization isn&#x27;t necessary at all. If the code controls response to a tab selection, then the code that redraws the tab is likely to be executed in a separate thread, anyway, and done at the pleasure of the OS. Why bother optimizing the lookup index to save a few microseconds?<p>Another matter, entirely, when we are iterating an Array that is many thousands of elements long. In some cases, using HOF can actually decrease the performance (but YMMV). I have sometimes had to replace a <i>map()</i> with a <i>for</i>.<p>We measure and find hot spots, and then concentrate on them.<p>If we are working with mobile or embedded, then we also need to worry about power consumption. That&#x27;s a fairly fraught area, right there, and optimization can actually cause power drain.
评论 #21938572 未加载
mirekrusinover 5 years ago
The takeaway should be - run profiler at least once before hiring extra architects and spending half a million on hardware&#x2F;licenses.
pdfernhoutover 5 years ago
Been trying to get WordPress to optimize memory usage for four years on this ticket: <a href="https:&#x2F;&#x2F;core.trac.wordpress.org&#x2F;ticket&#x2F;34560" rel="nofollow">https:&#x2F;&#x2F;core.trac.wordpress.org&#x2F;ticket&#x2F;34560</a> &quot;Right now, you will unhappily see &quot;500 server error&quot; and &quot;white screen of death&quot; results eventually if you, say, edit a 400K page for hundreds of revisions, even with a 256MB server memory limit. ... There are apparently <i>three</i> requests for all posts versions being made by the (Page) editor.&quot;<p>That might be some record <i>both</i> for inefficient coding and then for not caring much about inefficient coding and all the extra expense millions of WordPress users face to host such inefficient code? Either that or maybe few WordPress users make many edits to large pages?
dekhnover 5 years ago
One of the more interesting optimizations I&#x27;ve seen is the C++ string class. A class instance takes up 24 bytes, many of which weren&#x27;t used, so for short strings the data was stored inline rather than having a pointer to external memory. This is big if you have an app that has millions of tiny strings.
评论 #21938719 未加载
raverbashingover 5 years ago
Premature optimization is not great, but for low hanging fruit, just do it.<p>As much as developer time is more expensive than machine time it seems people are forgetting best practices and&#x2F;or minor improvements that can have a big impact.
评论 #21938437 未加载
exabrialover 5 years ago
<p><pre><code> The form: Boolean b = Boolean.valueOf(true); Is slightly more efficient than the subjectively uglier: Boolean b = new Boolean(true); </code></pre> So couple of notes on that. The &quot;new&quot; operator is cheap, but still involves an allocation. Oddly enough, one of the strangest bugs I found back in the day was:<p><pre><code> Boolean a = new Boolean(true); Boolean b = new Boolean(true); System.out.println(a == b); false </code></pre> But with objects and wrapper types, the .equals() method is the correct way to compare two objects.
评论 #21939205 未加载
gwbas1cover 5 years ago
I really want to know more about &quot;why.&quot; Specifically, more about why the design of the system leads to creating tons and tons of empty hashsets.<p>Leads me to believe that there&#x27;s lots more meaningful optimizations remaining that someone who better understands the system could implement.
kazinatorover 5 years ago
&gt; As I found out while writing this article, modern JDKs do not allocate any space in a HashSet until something is added.<p>Ah, but the object still exists. If large space of objects is needed that is sparsely used, the thing to do is to make that space itself lazy, not the individual objects.
tudeloover 5 years ago
Most of my Java optimization attempts have ended in &#x27;oh, library x has deadlocks&#x27; where library x was necessary to use without massive time investments (big libraries like hibernate, oracle db drivers)...
phsover 5 years ago
Shucks! I came in here guessing it would be adding the trailing period on a domain name, to disable a long list of resolv.conf entries.
asveikauover 5 years ago
The article advises against applying this change everywhere, but I think this actually sounds like a good argument that the Java standard library should adjust the default constructor for Set. I am going to guess that Sets usually contain a small number of members. Paying memory allocation costs [amortized constant time] for large sets sounds a lot better than requiring memory to fit the possible range of values for small ones.
评论 #21938016 未加载
评论 #21938150 未加载
unilynxover 5 years ago
The Windows &#x2F;3GB bootflag might have also given the needed 0.5GB of extra heap space, but apparently the JVMs couldn&#x27;t really make use of it according to <a href="https:&#x2F;&#x2F;stackoverflow.com&#x2F;questions&#x2F;21631167&#x2F;java-heap-space-and-the-ram" rel="nofollow">https:&#x2F;&#x2F;stackoverflow.com&#x2F;questions&#x2F;21631167&#x2F;java-heap-space...</a>