22 ms·
The most copied StackOverflow snippet of all time is flawed (2019)
- code_duck 5y agoMy top Stack Overflow answer of all time is a now rather dated two lines of JavaScript: how to tell if a variable is undefined. I posted this in 2010 and have been getting points for it steadily for a decade, now exceeding the amount I garnered from all other activities while actively using the site. I don’t do js anymore but from what I understand the answer hasn’t been accurate since 2016 or something.
- jka 5y agoThere might be an opportunity somewhere around this area to combine the versioning, continuous improvement, and dependency management of package repositories with the Q&A format of StackOverflow. Something like "cherry pick this answer, with attribution, and notifications when flaws and/or improvements are found". Maybe that's a terrible idea (there's definitely risk involved, and the potential to spread and create bad software), but equally I don't know why it would be significantly worse than unattributed code snippets and trends towards single-function libraries.
- fennecfoxen 5y agoNodeJS did something a lot like this by having packages that are just short snippets, but half the ecosystem flipped out when someone messed up `leftpad`.
- fastball 5y agoWell that and because having 20,000 packages in your project is a PITA in various ways. Mostly but not entirely because NPM handled things poorly in various ways.
- deleted 5y ago[deleted]
- DylanSp 5y agoNot sure if it's quite what you had in mind, but SO is starting to address the issue of updating old answers with the Outdated Answers Project: https://meta.stackoverflow.com/questions/405302/introducing-outdated-answers-project https://meta.stackoverflow.com/questions/405302/introducing-...
- jka 5y agoVery relevant, thank you!
- Smithalicious 5y agoSadly updates don't just remove bugs, but sometimes also add them. Silently adding a bug to previously working code is a lot more bad than silently fixing a bug you didn't know you had is good, so I wouldn't want to have a load of self-updating code snippets in my codebase.
- pkaye 5y agoNow the new code is unreadable.
- ape4 5y agoIts as easy as "KMGTPE"
- bla3 5y ago> At the very least, the loop based code could be cleaned up significantly. Seems like the loop based code wasn't so bad after all...
- meetups323 5y agoLoop code has the same bug.
- bla3 5y agoThis is Java, not JavaScript. The exponents table was likely of integer type. Then it works.
- alisonkisk 5y agoHow does that avoid the misrounding bug for 999,999B = 1000KB (wrong), 1MB correct?
- bla3 5y agoD'oh, you're right.
- spkm 5y agoThis! If I had to choose between the two snippets I would have taken the loop based one without a second though, because of its simplicity. The second snippet is what usually happens when people try to write "clever" code.
- dataflow 5y agoThe loop by itself isn't entirely clear on what it's doing. Stuff like the direction of the > comparison and what to do vs. >= and the byteCount / magnitudes[i] at the end really do require you to pause & do mental analysis to check correctness. I think the real solution here is to define an integer log (ilog()?) function based on division and use that in the same manner as the log(). That way you only do do the analysis the first time you write that function, and after that you just call the function knowing that it's correct.
- colejohnson66 5y agoWhat’s wrong with a simple loop (like the one near the top)? Why does it have to branchless? Wouldn’t the IO take longer than missed branches/pipeline flushes? Not to mention that the fixed version now has branches as well…
- MauranKilom 5y agoThe irony is that a single log computation is going to take longer than the loop. (No idea if implementing a log approximation involves loops either.)
- deleted 5y ago[deleted]
- kortex 5y agoWaiting for someone to post some fast-inverse-sqrt-esque hack to compute the logarithm. Although in Java that's probably not likely to be faster. I wonder how fast it'd be to convert to string and count digits.
- Gibbon1 5y ago> I wonder how fast it'd be to convert to string and count digits. When you convert the number to a string you're really transforming it to a decimal format. Which is the domain where you should be solving the problem. Otherwise you're doing some sort transformation in the binary domain and then hopping to pull the answer out of a hat when you do the final convertion to decimal.
- bottled_poe 5y agoSounds like textbook example of when theory is misaligned with reality.
- slavik81 5y agohttps://code.woboq.org/userspace/glibc/sysdeps/ieee754/dbl-64/e_log.c.html https://code.woboq.org/userspace/glibc/sysdeps/ieee754/dbl-6... I don't see any loops, but there are a number of branches. The code could probably be generalized using loops to support arbitrary precision, but I think any optimized implementation for a specific precision will have unrolled them.
- kmote00 5y agoUpdate title: this is from 2019
- bsaul 5y agoseems that most comments here missed the end of the article , where he points to the "production ready" version of the solution, that is indeed very close to the original one, including a while loop.
- t0astbread 5y agoIt's especially ironic given that this is about a StackOverflow code snippet that many people probably also copied without reading.
- TwoBit 5y agoNeither is production ready because they have no code comments. And if ever there was code requiring comments, this is it.
- zoomablemind 5y ago> ..."production ready" version of the solution, that is indeed very close to the original one, including a while loop. What's missing still is a comprehensive set of test cases to check against. If such cases were spec'ed to go along with the original code, fthen at least one could have seen the applicability range and perhaps other people would have added some challenging corner cases (just as mentioned in the OP).
- eutectic 5y agoThis is why it's a good idea to have a real integer type.
- enriquto 5y agoIsn't it impossible? Integers go arbitrarily large but computers don't.
- asdf3243245q 5y agoComputers also go arbitrarily large. Not infinite, but arbitrarily large. A real number type could be bounded by the amount of RAM you have.
- alisonkisk 5y agoYou can use disk storage too. And network storage.
- btilly 5y agoIt is possible within the limits of available memory on the computer. Rather than the usual limit of a fixed number of bits. I've ironically found that big integer libraries sometimes optimize math routines more than string conversion. This was quite annoying for me when I optimized the factorial function in Ruby, and found that generating the string was my bottleneck. I then optimized that as well. :-)
- Sohcahtoa82 5y agoThey can go large enough for anything that matters. A quick Google says there's an estimate of 10^78 to 10^82 atoms in the universe. That number would be able to be stored in well under 300 bits.
- ithinkso 5y agoUniverse is tiny compared to mathematics and software, even simply RSA keys are already 2048bit. Lots of problems suffer from 'combinatorial explosion' [1]. I recently learned about the Archimedes's cattle problem, the solution is of order 10^206544 [2] [1] https://en.wikipedia.org/wiki/Combinatorial_explosion https://en.wikipedia.org/wiki/Combinatorial_explosion [2] https://en.wikipedia.org/wiki/Archimedes%27s_cattle_problem https://en.wikipedia.org/wiki/Archimedes%27s_cattle_problem
- jrockway 5y ago> Sebastian then reached out to me to straighten it out, which I did: I had not yet started at Oracle when that commit was merged, and I did not contribute that patch. Jokes on Oracle. Shortly after, an issue was filed and the code was removed. Good thing it wasn't a range check function. I hear those are expensive.
- dokem 5y agoSomething about this comes off as amateurish. The obsession with minimization. Just use a switch statement. Now where is the bug going to hide? The solution doesn't need to generalize, there is only a small handful of different solutions. Just break them all out. It's more maintainable and readable and requires less thinking.
- TwoBit 5y agoI don't know why you are being downvoted. The best solution here is for the author to admit using log was a bad idea and rewrite an entirely different version.
- deleted 5y ago[deleted]
- unwind 5y agoI must admit I smiled at seeing that I edited the question, back in the day. :) Can't say I remember the question, and didn't know it has that epic feature of being the most-copied. Cool!
- beermonster 5y ago> I wrote almost a decade ago was found to be the most copied snippet on Stack Overflow. Ironically it happens to be buggy. I don’t find it ironic, I find it quite normal that even small snippets of code contains bugs (given the daily review requests I receive). I think when copying code literally from StackOverflow what’s more important is understanding what the code does, and why , rather than copying it ad-verbatim by copy & pasting it into your production code. I also often find on StackExchange et al that quite often the most upvoted is the one that ‘fixes it’ for ‘most people’ yet the correct answer is down at number 3 or 4. Again, understanding the answer and why it applies, helps give you the context to understand if this is actually the solution to your problem or just treats the symptom.
- megalodon 5y agoOne of the best tips I have gotten from the internet is to never copy and paste code you have not written yourself. Even rewriting it verbatim makes you think about what it is you are actually copying. It's a pretty neat rule to have in mind.
- deleted 5y ago[deleted]
- corobo 5y agoWhen you get into this habit it also makes it easier to translate solutions from other languages too
- deleted 5y ago[deleted]
- dcow 5y agoIt's also good legal advice. It's now legally possible for you to copy and paste code directly from stack overflow because they made an effort to assert a compatible license over works published on their site. However, the same can't be said for most other code snippets flying around out there.
- AceJohnny2 5y ago> Key Takeaways: > [...] > Floating-point arithmetic is hard. I have successfully avoided FP code for most of my career. At this point, I consider the domain sophisticated enough to be an independent skill on someone's resume.
- RhysU 5y agoJust this week I watched someone discover that computing summary statistics in 32-bit on a large dataset is a bad idea. The computer science curricula needs to incorporate more computational science. It's a shame to charge someone tens of thousands of USD and to not warn them that floating point has some obvious footcanons.
- bigiain 5y ago> Just this week I watched someone discover that computing summary statistics in 32-bit on a large dataset is a bad idea. The computer science curricula needs to incorporate more computational science. Sadly, I suspect too many "computer science" courses have turned into "vocational coding" courses, and now those people are computing summary statistics on large datasets in Javascript...
- bqmjjx0kac 5y agoCould you shed some light on what they did wrong, and what would be a better way to do it?
- cellularmitosis 5y agonot OP, but the hint is in “computing summary statistics in 32-bit on a large dataset”. A large dataset means lots of values, maybe we can assume the number of values is way bigger than any individual value. Perhaps think of McDonalds purchases nation-wide: billions of values but each value is probably less than $10. The simplest summary statistic would be a grand total (sum). If you have a good mental model of floats, you immediately see the problem! The mental model of floats which I use is 1) floats are not numbers, they are buckets, and 2) as you get further away from zero, the buckets get bigger. So let’s say you are calculating the sum, and it is already at 1 billion, and the next purchase is $3.57. You take 1 billion, you add 3.57 to it, and you get... 1 billion. And this happens for all of the rest of the purchases as well. Remember: 1 billion is not a number, it is a bucket, and it turns out that when you are that far away from zero, the size of the bucket is 64. So 3.57 is simply not big enough to reach the next bucket.
- tasty_freeze 5y agoThe thing that jumped out at me, as I've seen the same kind of thing on the job, is the assumption that, eg, log(1000)/log(10) is exactly 3. Does the standard guarantee that the rounded approximation of one transcendental number by the rounded approximation of a related transcendental number will give 3.0 and not 2.999999999?
- remram 5y agoYeah that seems like a serious flaw to me too. On my Python: >>> math.log(1000)/math.log(10) 2.9999999999999996 >>> int(math.log(1000)/math.log(10)) 2 But I don't know about the guarantees provided in the JavaScript standard (or more importantly those offered by actual browsers).
- halter73 5y agoFloating point math is IEEE 754 in pretty much all cases, so you should see this result in most languages. `math.log(1000, 10)` gives the same result because it's implemented using natural logs internally as it is in most languages. In this case, there's only about six boundary cases to consider so you can just manually verify it works as expected.
- danellis 5y ago> almost no branches I wonder whether the author is suggesting that (potentially) nine branches is a small number, or they overlooked ternary expressions and function calls and are just counting the if statement.
- TwoBit 5y agoThere are tons of branches in those log and pow calls. Programmers are lost in branch free religion.
- axiosgunnar 5y agoSo it's not flawed (it does compute the correct result). The author just thinks a completely unreadable (but supposedly faster) variant using logarithms is "better" than the simple loop used in the original snippet? Write your code for junior devs in their first week at your company, not for academic journals.
- hardwaregeek 5y agoI think you might have misread the post. His logarithm code became the most used snippet and had the bug.
- deleted 5y ago[deleted]
- deleted 5y ago[deleted]
- deleted 5y ago[deleted]
- ascar 5y agoHis code snippet had rounding errors on the boundaries towards the next unit. However he notes: > FWIW, all 22 answers posted, including the ones using Apache Commons and Android libraries, had this bug (or a variation of it) at the time of writing this article.
- phist_mcgee 5y agoYou should almost _always_ focus on code readability and simplicity over inventiveness and cleverness. Very few people I have encountered have complained about code being 'too simple' or 'too readable', but the opposite happens on a near daily/weekly basis. Write comments, use a for loop, avoid global state, keep your nesting limited to 2-3 levels, be kind to your junior devs.
- djur 5y agoWhat does "use a for loop" mean here? Aren't for loops infamously difficult for new programmers to understand?
- penteract 5y agoThis is a bit of a tangent, but while it may be conventional to round to the value with the smallest difference, is that convention good? In a case such as this where it's fine for the prescision to vary with magnitude, then I'd argue it makes sense to round to the value with the smallest ratio.
- jasonhansel 5y agoIMHO any code that tries to perform floating-point arithmetic on integer values and then produce exact output should be considered suspect in and of itself...too many edge cases.
- leephillips 5y agoWhat sticks out for me is that people don’t even rename functions when copypasting from SO.
- sgarman 5y agoI know everyone is on their high horse about copying code but if you were/are to copy code keeping it the same is super valuable because invertible when someone comes a long later googling it will take them to where it was copied from originally.
- kalleboo 5y agoWhen I'm "inspired" by code from somewhere, I go ahead and put the URL in there in a comment
- amelius 5y agoWouldn't it be cool if you could call stack overflow answers directly from your code?
- hardwaregeek 5y agoFloating point is really really hard to get right, especially if you want the numbers to be stable. Which begs the question, why the heck does JavaScript, the most used language in the world, not have an integer type? Sure, there's BigInt but that's quite clunky to use. I know it's virtually impossible to add by now, but I'd love a integer type for all my bit twiddling, byte munching needs.
- ascar 5y agoI just feel if you have bit twiddling, byte munching needs JavaScript shouldn't be the language of choice. Doing that is a rather rare edge case and if you're doing it for performance reasons, working in Javascript is the much bigger performance problem.
- hardwaregeek 5y agoThat may be true but another case where floating point should be avoided is with money. Now think about all the times a web developer innocuously used a JS number to represent a price. I wouldn’t be surprised if floating point errors affected billions of dollars of transactions.
- btilly 5y agoIf you're already using JavaScript for some other reasons but occasionally have bit twiddling, byte munching needs, then trying to do that in JavaScript makes perfect sense. Is it the fastest option? No. But according to https://benchmarksgame-team.pages.debian.net/benchmarksgame/fastest/node-gpp.html https://benchmarksgame-team.pages.debian.net/benchmarksgame/... it is generally within a factor of 4-5 of C++. For an application area where this applies, consider a web-based game. Using JavaScript keeps you from shipping another application. But occasionally you may have bit twiddling and/or byte munching needs. Which you need to do in JavaScript.
- ascar 5y agoMy point wasn't to say you should never do byte manipulation in Javascript, but that for these rare edge cases the existing capabilities without a native int are fine and if you would really need the native int rather than some equivalent work around (which I assume is most likely due to performance considerations) a faster language is the better approach. A webgame might be able to use wasm for that.
- mjevans 5y agoThe author's lookup table is incorrect. The question being answered clearly wanted base2 engineering prefix units, rather than the standard base10 engineering prefix units. suffixes = [ "EB", "PB", "TB", "GB", "MB", "KB", "B" ] magnitudes = [ 2^60, 2^50, 2^40, 2^30, 2^20, 2^10, 2^0 ] // Pseudocode, also 64 bit integers required. (Compilers might assume unsigned 32 for int)
- returningfory2 5y agoThat code snippet is explicitly introduced in the article as not the author's.
- asdf3243245q 5y agoThat is not the author's code. That is pseudocode for one of the example answers that he is improving on. The author's code gives an option for the units: int unit = si ? 1000 : 1024;
- Fornax96 5y agoIf you do this you should add an 'i' to the prefixes to denote that you mean the binary notation. e.g: kiB, MiB, GiB, TiB, etc
- stefan_ 5y agoWhy are you writing code? The question was for a static method in Apache Commons, not your "I'm so clever" implementation. Think the reading comprehension is flawed. (Of course, this static method exists in Apache Commons, going back at least 20 years. But the fellow "code golfers" of the author voted someone to the first answer who similarly had the irresistible urge to try to be very clever. It's a scourge on StackOverflow.)
- opheliate 5y agoI think that the answer is what I would expect based on the question title (which doesn’t mention Apache Commons, only Java), if I was another user searching for the solution to this problem. Maybe the question should have been renamed to indicate this, but as it stands, I do think a library-agnostic solution is more helpful to people finding the question than an answer which only works for Apache Commons.
- mweberxyz 5y agoSay what you want about the stability of the npm ecosystem, but if this were JS, a new SemVer patch release could be cut, and it would be fixed in thousands of code bases essentially instantly.
- devit 5y agoYou have to be a terrible programmer to even consider using a base 10 logarithm for this. Their proposed improvement is also terrible, since it divides multiple times unnecessary, and checks for negativity multiple times unnecessarily. The proper simple solution is of course a handwritten binary search with if-else blocks that starts with the most likely range, annotated with "likely" annotations, and a single division. If this is the main task of the program for a while, and thus a large fraction of the cache can be dedicated to it, then solutions with large lookup tables are worth trying (obviously optimizing string formatting is also essential in this case). This is why software is so often broken, there's a lot of incompetent people programming.
- winrid 5y agoYou're right, however I think they were going for a "branchless" version just to see if they could.
- simonw 5y ago"You have to be a terrible programmer to even consider using a base 10 logarithm for this." That's not a fair statement. Good programmers are programmers who deliver value - who build robust, maintainable features in reasonable time that address user needs. Whether or not you would quickly find the correct approach to this specific problem is a miniscule, pedantic detail in a giant ocean of programming skills and experiences.
- juped 5y agoYou are replying to a satirical comment, I think.
- Aeolun 5y agoYou may think that, but I’m partial to the ‘for-loop version’ that everybody and their dog can understand.
- hvdijk 5y agoAbout the "terrible" aspect of it, to quote: "Granted it’s not very readable and log / pow probably makes it less efficient than other solutions. But there were no loops and almost no branching which I thought was pretty neat." No need to insult the author over it. About your "proper simple solution": I don't think that's a good idea either. Based on your next paragraph, the version you suggest with the handwritten binary search and "likely" annotations is for the case where the code isn't performance critical: for where the code is performance critical, you suggest a different solution. If the code isn't performance critical, please do not turn it into an unreadable mess over what would become a negligible overall performance gain. Write it in a simple, obviously correct way, keep it boring, and you'll keep it stable; you can use the time you save on fixing bugs in your super optimised version on improving more critical parts of your program.
- yesenadam 5y ago> The most copied StackOverflow snippet of all time Maybe, but sounds like it's merely the Java snippet from SO found most often on github. Not sure why blog author didn't include the word "Java" in his title or the first paragraph: > an answer I wrote almost a decade ago was found to be the most copied snippet on Stack Overflow There is no evidence for this claim in the blog post, just that it's the "most copied Java snippet". And it's just based on occurrences in github. Maybe the most-copied snippet is an AWK or ffmpeg one-liner? Something that wouldn't find its way into a github repo. Or maybe something undetectably vanilla, like answers to "How do you write loops in language X?" Is there a way of finding out what actually is the most-copied snippet?
- sgerenser 5y agoI don’t know how you’d find it, but if I had to bet it would be something to do with git.
- maest 5y agoThis reminds me of my favourite SO answer: https://stackoverflow.com/a/40429822/864112 https://stackoverflow.com/a/40429822/864112 It boggles the mind that anyone could ever suggest this as a solution.
- deleted 5y ago[deleted]
- kortex 5y agoEw. Yikes. Wow, that's a special kind of special. The mind truly boggles. It had a score of 4 when I first checked it, but it looks like it got slashdotted by this thread/link and now it's -1 and probably still falling. Good.
- esnard 5y agoAt the time I'm writing this, the answer got 3 upvotes, 13 downvotes and 1 delete vote since the link has been posted: https://stackoverflow.com/posts/40429822/timeline?filter=WithVoteSummaries https://stackoverflow.com/posts/40429822/timeline?filter=Wit...
- kortex 5y agoTIL: that timeline feature is really neat! I don't see a way to get to it from the mobile UI though, will need to hunt around.
- arduinomancer 5y agoI'm going to choose to believe that is a joke answer
- klyrs 5y agoWow. Nice comment... > This is akin to answering "how do I bake a cake?" with "open up a bakery, walk inside, and ask for a cake" Only it's more like answering "how much does this cake cost" by purchasing the cake and looking at the receipt.
- dathinab 5y agoThis specific example is a good example why you should keep code as simple as possible, and why even "simple" math needs special care when testing (Because floats are not simple.)
- cratermoon 5y agoReminds me of this article on roman numerals https://kevlinhenney.medium.com/out-of-control-97ed6efa2818 https://kevlinhenney.medium.com/out-of-control-97ed6efa2818
- anonymfus 5y ago> return String.format("%.1f %sB", bytes / Math.pow(unit, exp), pre); As a human, the first thing that I hate about this interpretation of "human readable" format is inconsistency in the number of significant digits. One digit after decimal separator is simply wrong, as when you jump from 999.9 MB to 1.0 GB you go from 4 significant digits to 2, instead it should be 1.000 GB, 10.00 GB and so on. This annoys me enormously when I upload things to Google Drive from Android phone and look at the number of data transferred as as soon it becomes bigger than 1 GB digits stop changing and I become anxious that it stopped the transfer and my Windows Phone nostalgia jumps over the roof (as WP was never infected with this problem by virtue of not using Java, and OneDrive on WP explicitly showed current connection speed, and frozen connection never caused any strange problems with uploaded files like it does on Google Drive on Android). As a human not from US, the second thing I hate here is lack of locale parameter to pass to formatter as decimal separator is different in different cultures, and in the world of cloud computing the locale of the machine where the code is run is often different from the one where the message is displayed. As a human from a culture using non latin alphabet, the third thing I hate here should be obvious for a reader.
- anonymfus 5y agoAs a bonus, the thing I don't care any more here is that there is no option to output binary SI prefixes.
- Kiro 5y ago> instead it should be 1.000 GB, 10.00 GB and so on I had a hard time mentally parsing that sequence even when I knew what your point was so imagine regular users seeing that.
- cycomanic 5y agoI don't think it makes sense to talk about significant digits here. And while you are correct that you should not go from 999.9MB to 1.0 GB you are incorrect about your reasoning and your correction is also incorrect. Significant digits signify reliability of the numbers. So if your measurement is accurate to the +/- 50kB as indicated by 999.9MB you should then move to 1.0000 GB (5 significant digits). So it should be 10.00GB and 1.00GB not 1.000GB, because the reliability should not change between your measurements.
- css 5y agoI like the way v8 handles this problem: https://github.com/v8/v8/blob/dc712da548c7fb433caed56af9a021d964952728/tools/zone-stats/helper.js#L10-L19 https://github.com/v8/v8/blob/dc712da548c7fb433caed56af9a021...
- bombcar 5y agoIt seems to me that the elegant solution would involve an instruction that returns the first non-zero bit of the number - but I don’t know if such a instruction exists in assembly.
- muricula 5y agoBasically lzcnt or leading zero count on x86: https://www.felixcloutier.com/x86/lzcnt https://www.felixcloutier.com/x86/lzcnt
- ac42 5y ago> It should be noted that on processors that do not support LZCNT, the instruction byte encoding is executed as BSR. This. Boggles.
- bombcar 5y agohttps://stackoverflow.com/a/43443701 https://stackoverflow.com/a/43443701 - interesting - it seems to be a side effect of changing meaning of an instruction.
- deleted 5y ago[deleted]
- ddlatham 5y agoI'm the author of #6 on the same list. It's definitely interesting to see it has been used thousands of times on GitHub, and who knows how many more in proprietary code. I don't think it's buggy, but I now think it could definitely be improved. I think this shows an example of a big problem with StackOverflow compared to its initial vision. I remember listening to Jeff and Joel's podcast, and hearing the vision of applying the Wikipedia model to tech Q&A. The idea was that answers would continue to improve over time. For the most part, they don't. I'm not quite sure if it's an issue of incentives or culture. Probably some of both. I think that having a person's name attached to their answer, along with a visible score really gives a sense of ownership. As a result, other people don't feel enabled to come along and tweak the answer to improve it. Then, once an answer is listed at the top, it is given more opportunity for upvotes, so other improved answers don't seem to bubble up. This is a larger issue with most websites that sort by ratings. Generally they sort items based on the total number of votes, including hacker news itself. Instead, to measure the quality of an item, we should look at the number of votes, divided by the number of views. It may be tough to measure the number of views of an item, but we should be able to get a rough estimate based on the position on a page, for example. If the top comment on a HN discussion is getting 100 views in a minute and 10 upvotes, but the 10th comment down gets 20 views and 5 upvotes, the 10th comment is likely a better quality comment. It should be sorted above the top ranked comment! There would still need to be some smoothing and promotion of new comments to get them enough views to measure their quality as well. Such a policy on StackOverflow would also help newer, but better answers sort to the top.
- analyte123 5y agoWhat would really help with the vision here is some way to comment and associate tests against posted code. I have corrected algorithms on Wikipedia that were obviously wrong with even a cursory test. Then people can adjust the snippet, debate the test parameters, or whatever else they need to do while maintaining some sort of sanity check. If it’s good enough for random software projects used by a dozen people, it’s probably good enough for snippets used by thousands of developers and even more users.
- 5y ago
- cottsak 5y agois it reasonable to assume a strong correlation between "copied code" and number of upvotes? #trolling #kiddingnotkidding
- lilyball 5y agoWhen the author started introducing all the calculations to figure out if the printed version would round up, my first thought was, why not just look at the printed version? Print it as %.1f, then chop off anything past the period and re-parse it as an integer. Now you can trivially tell if it rounded up past the threshold and you need to bump the suffix.
- kylejrp 5y agoAs part of the Stack Overflow April Fools' prank, we did some data analysis on copy behavior on the site [0]. The most copied answer during the collection period (~1 month) was "How to iterate over rows in a DataFrame in Pandas" [1], receiving 11k copies! [0] https://stackoverflow.blog/2021/04/19/how-often-do-people-actually-copy-and-paste-from-stack-overflow-now-we-know/ https://stackoverflow.blog/2021/04/19/how-often-do-people-ac... [1] https://stackoverflow.com/a/16476974/16476924 https://stackoverflow.com/a/16476974/16476924
- audiometry 5y agoThat’s sad, as when you find yourself iterating over rows in pandas you’re almost invariably doing some wrong or very very sub optimally.
- dannyw 5y agoTo me it's an means to an end. I don't care if my solution takes 100ms instead of 1ms, it's the superior choice for me if it takes me 1 minute to do it instead of 10 minutes to learn something new.
- bruce343434 5y agoThe flaw of human nature on display. And I don't mean that personal, not to you anyway, but to the human species.
- coopsmoss 5y agoWhy? It seems very rational. Especially if you're just going to run it once to get a value and not as a part of some system.
- kamray23 5y agoExactly, that's not a flaw, that's rational behaviour. Why design an intricate solution for a one-off. Using 15 times the amount of time it would have taken you manually to automate a pretty standard task is just stupid, though we all do it. Do the first thing that works, don't overthink it.
- comicjk 5y agoWhen I'm explaining logarithms, I find it helps to relate it to the number of digits. This code is a good example of the concept: you don't need log, just convert the int to a string and check its length. A string with 1-3 digits is bytes, 4-6 is kb, etc.
- foysaluix 5y agoAt the very least, the loop based code could be cleaned up significantly.
- Smithalicious 5y agoI don't think this works very well as a cautionary tale because honestly, I would not even care about a bug like this. It's something very few people would even figure out exists at all, it's incredibly inconsequential.
- cellularmitosis 5y agoYou’ve made a judgement call that correctness isn’t a priority in this circumstance, and as long as your judgement is sound, this approach will serve you well. The weakness of your approach is that no one’s judgment is sound 100% of the time. Alternatively, folks who always prioritize correctness may occasionally “waste their time”, but two things to consider: 1) their judgement is no longer an issue, and 2) in the long run they have spent more time training their correctness muscles and are in better shape.
- wongarsu 5y agoHowever this "bug" is still entirely within spec. The whole article hinges on "the 1,000 “significand” is out of range according to spec", but it really isn't. 999999 Bytes are indeed around 1000kB. Sure, calling it 1MB would be preferable, but saying 1000kB doesn't violate any rule, is perfectly acceptable according to SI (just like I can say 1000g or 1kg interchangeably), fulfills the task of being human readable, and in all the examples given in the task the code behaves as requested. Sure, the code doesn't do exactly what the programmer wanted. But that doesn't necessarily make it incorrect.
- deepsun 5y agoDoes Math.log really faster than simple loop with just a couple of iterations after JIT compilation?
- cellularmitosis 5y ago> Granted it’s not very readable and log / pow probably makes it less efficient than other solutions
- zgs 5y agoThe proposed solution is crazy. Logarithms are extremely expensive to compute. No way is this code more efficient than the loop it "replaced". That there then are numeric stability issues and a pretty gross fudge factor is used to fix them worsens the situation. I would have a quiet word with any programmer I worked with that came up with this "solution".
- deleted 5y ago[deleted]
- 8bitsrule 5y agoOverkill. KISS. n counts moving the decimal left 3 places until there are <=3 digits left. Keep one place to the right. "BKMGTPE". n==0 => 'B'; n==4 => 'T'. 810 has 3 digits. n==0, 810B. 999950 has 6 digits. n==1, you've got 999.9K 1100000 has 7 digits. n==2, 1.1M 1234567890 has 10 digits. n==3, 1.2G
- throwaway4good 5y agoHonestly. The code is fine. This is for presenting stuff in a user interface. Who cares if you can find some weird edge case using MAX_LONG and MAX_DOUBLE which never will occur in practice.
- Cthulhu_ 5y agoUntil it does.
- throwaway4good 5y agoReadability and maintainability matters far more. And no - the edge cannot occur as it would require a file / whatever to have that size.
- throwaway4good 5y agoFor example - what is the meaning of the parameter "si"? I betcha that is going to give you more bugs than the edge cases discussed here.
- ayewo 5y agoThe parameter "si" here stands for International System of Units, or SI for short [0]. 0: https://en.wikipedia.org/wiki/International_System_of_Units#SI_metric_prefixes_and_the_decimal_nature_of_the_SI_system https://en.wikipedia.org/wiki/International_System_of_Units#...
- moring 5y agoThe original doesn't have types, but the modified version of humanReadableByteCount() uses a "long bytes" and as such will fail if the file size is (Long.MAX_VALUE+1) because it cannot even accept the correct size as its argument in the first place. Implementing these edge cases makes adds one more working case to 2^63 (2^64 if negative file sizes are valid) when the bigger problem is using the type "long" when files of that size are possible on the target system.
- Tempest1981 5y agoShows how much people enjoy writing code (puzzle solving) and hate writing unit tests.
- aristophenes 5y agoIt disturbs me that the authors answer became the top answer. It didn’t have a loop but was less efficient than the already accepted answer, and worse, much more complicated for a human to read and understand. It seems we are always drawn to be clever, when perfection is found in simplicity.
- Torakfirenze 5y agoInteresting how the same things crop up over time. I remember seeing this on HN when it was written in 2019 :) https://news.ycombinator.com/item?id=21698619 https://news.ycombinator.com/item?id=21698619 Still, a good lesson!
- jedimastert 5y agoFun fact: The reason Safari/Chrome/Firefox had to freeze the MacOS version in the User-Agent string is because of a code-snippet from StackOverflow that assumed the version started with "10" that snuck its way all over the place, including the Unity web player and a major wordpress templete.
- williesleg 5y agoChina bots
- deleted 5y ago[deleted]
- ChrisArchitect 5y agoprevious discussion: https://news.ycombinator.com/item?id=21698619 https://news.ycombinator.com/item?id=21698619
- jozvolskyef 5y agoCoincidentally I had to write this today, and perplexingly none of the answers on that popular question seem to be as efficient and readable as what I wrote: function prettyPrintBytesSI(x: number): string { const magnitude = Math.abs(x) if (magnitude < 1e3) return `${x} B` else if (magnitude < 1e6) return `${x/1e3} kB` else if (magnitude < 1e9) return `${x/1e6} MB` else if (magnitude < 1e12) return `${x/1e9} GB` else if (magnitude < 1e15) return `${x/1e12} TB` else if (magnitude < 1e18) return `${x/1e15} PB` else return `${x} B` }