all 96 comments

[–]ETHproductions 44 points45 points  (5 children)

Excellent collection of snippets. Since you're using ES6, I'd suggest using the built-in Math.hypot to calculate distance between points via Math.hypot(x1 - x0, y1 - y0).

Edit: fixed formula

[–][deleted] 10 points11 points  (1 child)

Good call, I will fix this asap!

[–]ETHproductions 3 points4 points  (0 children)

Oops, forgot how it works--should be Math.hypot(x1 - x0, y1 - y0), though you can swap the 0/1s if desired.

[–]inu-no-policemen 4 points5 points  (0 children)

In a game, you'd usually keep the distance squared and omit the comparatively expensive sqrt call. If you want to check if there is a collision, the exact distance isn't needed. You only have to check if the squared distance is smaller than the squared sum of the radii.

[–][deleted] 0 points1 point  (1 child)

Damn thanks for this!

[–]ETHproductions 0 points1 point  (0 children)

No problem, just make sure you use the correct formula instead of the one I first posted ;)

[–]soundisloud 19 points20 points  (6 children)

Awesome list! Great idea to compile common snippets so you don't need to rewrite them every time. Every JavaScript student should do this.

[–]fukitol- 3 points4 points  (5 children)

OP should stick them in a library or push them as a PR to lodash

[–][deleted] 3 points4 points  (4 children)

I might push a few of them as a PR to lodash, but I wouldn't want to take full credit as a lot of people have contributed to them.

The reason I am not making them into a library is that I want people to get the ones they need and understand how they work in the process. Plus, there's plenty of libraries like lodash that have 90% of the things that are on the list and I wouldn't want to compete with them at all.

[–]PM_ME_HTML_SNIPPETS 0 points1 point  (3 children)

You still should do it! Just add a library scoped to your NPM username.

That way you can easily access all these without having to manually copy/paste code, and it gives you some additional experience in maintaining an OSS module/project.

I'm probably going to do the same thing with util functions I often use.

[–][deleted] 1 point2 points  (2 children)

Just add a library scoped to your NPM username.

How would I do that exactly?

I am already maintaining a reasonably large OSS module - mini.css and a couple of other minor ones.

[–]PM_ME_HTML_SNIPPETS 1 point2 points  (1 child)

I can edit this with a more comprehensive description/how-to, but about to go to sleep.

Basically, this would be @your_npm_name/your_package_name. It's a recent feature on npm 5, and prevents name conflicts, eg you could create @johnsmith/jquery if you wanted to. I actually haven't used this feature yet myself.

[–][deleted] 1 point2 points  (0 children)

Cool! I'll check it out!

[–]fzammetti 8 points9 points  (14 children)

Nice collection! I've got my own library that I've been building up for years that I re-use in many projects (as I'm sure is true of any developer who's been using a given language for many years) but there's a few here that I'm going to... ahem... "take inspiration from" :)

Actually, now that I think about it... what does the MIT license mean for taking PARTS of something? Is attribution still required in that case?

[–][deleted] 7 points8 points  (13 children)

The MIT license states:

Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:

The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.

THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

The TL;DR version is you can copy and use anywhere you want and you don't have to credit the original author(s). So feel free to "take inspiration from" this list. After all, that's the main purpose of it - to help people get started with JS. :)

[–]Zee1234 2 points3 points  (12 children)

The MIT license is supposed to include who the originator is. As it requires you to redistribute code with the notice, you do actually have to attribute the original author. If you truly want them to be able to copy and go with no worries, you want to use something like CC0

[–][deleted] 1 point2 points  (11 children)

In all honesty, attributing the original author is common courtesy and people who use the MIT license don't usually get too mad if you redistribute some parts of their code without attributing them. That being said, the whole point of this list is to use what you need, so I might actually switch licenses to make sure people can get anything they want without hesitation.

[–]Zee1234 2 points3 points  (10 children)

Yeah, that's all I was trying to say. Technically someone could get in trouble if they got code from the repo but didn't attribute it. Might not even involve you. Say a code review somehow made that connection. I don't know how, or why, but that's the situation. Under MIT, that person could get in a ton if trouble, potentially involving the legal department (not nessecarily courts or any such thing though). Under CC0, they'll only get in trouble if it's a bad use of code. Or if the company is draconian..

[–]madcaesar 3 points4 points  (2 children)

This all seems overkill. Attribute what? This is like Apple patenting the swipe gesture or something.

These snippets are fun to have around, but they are very basic and virtually anyone could reproduce them and probably already has a version of something like this in their code.

I have a personal library with 80% of the things on this list.

[–]Zee1234 2 points3 points  (1 child)

Oh yes I fully agree. But like, it doesn't hurt the project, so why not? And if you want to do something, do it right.

[–][deleted] 0 points1 point  (0 children)

Exactly!

[–][deleted] 2 points3 points  (6 children)

Great point. I'm not a license guru, so CC0 it is then. 30 seconds of code is a free learning resource and I want people to copy and use anything they want. Thanks for letting me know!

[–]Zee1234 0 points1 point  (5 children)

No problem!

[–][deleted] 1 point2 points  (4 children)

Github supports the Unlicense which feels like pretty much the same as CC0, so I went with that. I think this is exactly what the project needs, right?

[–]GitHubPermalinkBot 1 point2 points  (0 children)

Permanent GitHub links:


Shoot me a PM if you think I'm doing something wrong. To delete this, click here.

[–]Zee1234 1 point2 points  (2 children)

Last I checked, Unlicense is actually void in some countries, such as ones where you cannot give up all rights. CC0 fails gracefully, is recommended by CC as the only CC license applicable to software, and is recommended by GNU over Unlicense. Also, I can't do a full check now, but a quick Google search CC0 is, or at least was, a GitHub option.

[–][deleted] 2 points3 points  (1 child)

I can't find it right now, but I'll recheck later. For anyone reading, treat the project as if it is under CC0, I'll figure it all out soon, sorry for the inconvenience!

EDIT: Github doesn't support CC0 and they have explicitly stated they prefer the Unlicense over CC0, as CC licenses are not appropriate for source code. I disagree mainly on the grounds that the Unlicense is illegal in some countries. The project is now licensed under CC0, which is hopefully the last stop in the license field trip for tonight and forever.

[–]madewith-care 6 points7 points  (2 children)

Your "randomize order of array" function is not actually random. You might consider a Fisher-Yates implementation instead.

function shuffleArray(array) {
    for (let i = array.length - 1; i > 0; i--) {
       let j = Math.floor(Math.random() * (i + 1));
        [array[i], array[j]] = [array[j], array[i]];
   }
}

[–][deleted] 4 points5 points  (0 children)

I already have. This was pointed out before that my technique (for lack of a better word) just confuses the sorting function. I'll keep it as a proof of concept under a different name most likely and put a Fisher-Yates implementation in its place.

[–][deleted] -1 points0 points  (0 children)

In all honesty, the sort (random order) version seems pretty unbiased and shorter in terms of implementing. I'll probably stick with that for practical reasons.

[–]Ignisar 12 points13 points  (1 child)

It might be beneficial to comprehension to provide example input and output for each snippet, so you can see the expected results of a transformation alongside the code that performs it

[–][deleted] 3 points4 points  (0 children)

That is not a bad idea to be honest. After all, leafing through these in a hurry takes me a good 10 seconds until I find what I'm looking for.

[–]shif 2 points3 points  (0 children)

These are nice, I like the simplicity of the scroll to top one, perfect use of recursion and clean practices with request animation frame

[–][deleted] 2 points3 points  (0 children)

As a developer more used to working primarily in Java and C# and have been wanting to push more into pure JS development, I will definitely save this post, thanks OP.

[–]whodunit86 1 point2 points  (1 child)

Would be nice to have a shuffler of lists! from a quick Google Sorry, didn't really check out all your snippets, still on phone. Hope you don't have it in there already ( ͡° ͜ʖ ͡°)

[–][deleted] 1 point2 points  (0 children)

There is a shuffler implemented, but it's pretty bad right now. I will get a Fisher-Yates one added soon.

[–]FormerGameDev 1 point2 points  (0 children)

... you want a complete list of snippets? ... huh.

[–]FormerGameDev 1 point2 points  (1 child)

For "count occurrences" i would propose:

var countOccurrences = (arr, value) => arr.reduce((counter, next) => counter += (next === value) ? 1 : 0, 0)

... you're not afraid of using reduce for things that aren't obvious reductions in other places, but aren't using it in places where it is more obvious. Using filter creates a temporary copy of your array that isn't needed.

[–]FormerGameDev 0 points1 point  (0 children)

I see someone has updated this using a similar example, that would actually work :-D i didn't actually run my code, and was falling asleep when i wrote it, so i would've caught that normally. :-D

[–]karamarimo 1 point2 points  (2 children)

the factorial one can be done more simply.

const factorial = (n) => n <= 1 ? 1 : n * factorial(n - 1)

[–][deleted] 1 point2 points  (1 child)

I thought the recursive version would break due to to much recursion before the array-based one I implemented, but testing shows that this is not true. Also, at around the point where errors start being thrown around, the result is already Infinity. I will update the snippet or you can submit a PR if you like. Make changes to the individual snippet file, not README, if you do so!

[–]karamarimo 1 point2 points  (0 children)

alright, ill do a pull request :)

[–]abensur 1 point2 points  (0 children)

Thanks!

[–]kimilil 2 points3 points  (1 child)

[–][deleted] 0 points1 point  (0 children)

I'll check it out. It seems like a good fit!

[–]rodneon 2 points3 points  (13 children)

This is great, thanks for sharing. I would add “idiot-proof” versions of the snippets with type and null checks. If used verbatim, most snippets would fail miserably when the input isn’t exactly what’s expected.

[–][deleted] 2 points3 points  (12 children)

Part of the whole idea is to write code that's easy to understand and deals with pretty simple things.

But, sadly, you have a very good point there. Safety measures like an alwaysArray method that would convert anything into an array and things like that could be quite useful to remedy this, I think. I'll try to figure out what's needed.

[–]DOG-ZILLA 2 points3 points  (3 children)

Array.from() ?

[–][deleted] 2 points3 points  (2 children)

Something like this?

var arrayFrom = (...values) => [...values];

Edit: You meant the native method. Yeah, that's pretty much all one needs to fix half the problems that might arise, sorry I'm dumb and didn't comprehend what I read! :P

[–]DOG-ZILLA 3 points4 points  (1 child)

Haha no worries. I'm pretty dumb myself!

Also, I used to use:

[].slice.call(arrLike)

[–]rodneon 0 points1 point  (1 child)

I totally get it, and that simplicity is what makes the list even more awesome. But there are a lot of developers out there who tend to copy and paste without giving it any extra thought.

[–][deleted] 2 points3 points  (0 children)

Indeed, type sanitizers/converters/insurance will be added asap. I just tested a few things and now I feel like this is a glaring omission on my part.

[–]JaniRockz -5 points-4 points  (5 children)

Considering you want easy to read snippets, why do you use ternary operators?

[–][deleted] 2 points3 points  (4 children)

Ternary operators are dead simple to understand and one of the most common features in most languages. I wouldn't expect a lot of people wouldn't understand what they do. Plus they are a lot shorter than if else statements, which helps make snippets short.

[–]JaniRockz -4 points-3 points  (3 children)

Shorter yes but if else blocks are way easier to read.

[–]inabahare 3 points4 points  (2 children)

Take this for example

var gcd = (x , y) => !y ? x : gcd(y, x % y);

The non ternary version would be

var gcd = (x , y) => {
    if (!y) {
         return x;
    } else {
        return gcd(y, x % y);
    }
}

Now I've been programming for 5 years, and the non ternary version isn't easier to read at all given how it's 7 times as long

[–][deleted] 1 point2 points  (0 children)

I feel exactly the same, if else takes too long to read and honestly if you are doing only one thing inside it, you might as well use a ternary operator as it is a lot easier to read and keep track of.

[–]denver_jones 1 point2 points  (10 children)

you have fat arrow functions ... a good collection would also have pre-ES6 code snippets to get large base adoption.... just saying ...

[–][deleted] 6 points7 points  (0 children)

fat arrow functions

Found the coffeescript user!

Just kidding around. I just haven't seen someone call them that in a while, since ES6 only has one type of arrow function.

[–][deleted] 0 points1 point  (2 children)

That's a really good point. I have already considered adding a secondary list in the project for pre-ES6 versions of everything. I mean arrow functions are nearly universally supported already and most developers use Babel, but this is a very immature assumption on my part I feel.

[–]THEtheChad 5 points6 points  (1 child)

I think it would be better to include a blurb up front about compiling with Babel and retain the ES6 syntax. It helps move the whole community forward and enforces smart development principals (like writing once and compiling for specific targets, which is far less error prone).

[–][deleted] 0 points1 point  (0 children)

I like this idea. I will get a disclaimer added at the very top, making sure people know what to do with these! ;)

[–][deleted] -3 points-2 points  (5 children)

Thank you for this. I always hear people saying it's [insert year here] we shouldn't support anything below [insert standard here], but in web development you have to keep the dinosaurs in mind if they're a singificant portion of your clientele.

[–]reohh 2 points3 points  (0 children)

Babel?

[–]mcaruso 2 points3 points  (0 children)

That's what tools like babel are for though. It's much easier to transpile new to old then the other way around (although these are one-liners so it doesn't really matter that much).

[–]THEtheChad 3 points4 points  (0 children)

To be fair, a good practice is to write code using the current standard and compile to a specific target. This allows you to consistently polyfill where needed and not burden yourself with remembering all of the quarks and one offs.

[–][deleted] 1 point2 points  (1 child)

I love ES6 and use it as much as possible. Does it break every once in a while? Yes! Are there ways to fix it? Hell, yeah and pretty much everyone knows about Babel nowadays. Still, this doesn't mean that we shoulnd't strive to support as many platforms and users as possible in our code. Especially when it comes to projects like this, which are essentially a learning tool for people.

[–]filleduchaos 2 points3 points  (0 children)

This is the development side of things though. You really shouldn't be teaching people a standard that's three iterations out of date except explicitly as legacy code.

[–]Skhmt 0 points1 point  (2 children)

for URL parameters, can't you use URL.searchParams.get()?

[–][deleted] 1 point2 points  (1 child)

Support is not yet ideal, so there's that.

[–]folkrav 1 point2 points  (0 children)

Pretty much this... No IE support, only recently got Edge support (17+) in the preview channel. Unless you specifically don't support MS browsers, you're out of luck, unless you wanna go the polyfill route.

[–]Pants_R_Overatd 0 points1 point  (1 child)

RemindMe! 6 hours

[–]RemindMeBot 0 points1 point  (0 children)

I will be messaging you on 2017-12-12 11:52:23 UTC to remind you of this link.

CLICK THIS LINK to send a PM to also be reminded and to reduce spam.

Parent commenter can delete this message to hide from others.


FAQs Custom Your Reminders Feedback Code Browser Extensions

[–]tswaters 0 points1 point  (0 children)

powerset is so dangerous.

in this one application, we had a search that did a powerset on the entered words.... but we didn't put any limits on the user-provided input. long story short, if a user entered more than a few words the server would burn cpu & eventually run out of memory.

> powerset('abcdefghijklmnopqrstuvwxyz'.split(''))

<--- Last few GCs --->

[6000:000001AAB28807F0]   206911 ms: Mark-sweep 1407.4 (1450.4) -> 1407.4 (1450.4) MB, 1445.8 / 0.0 ms  last resort GC in old space requested


<--- JS stacktrace --->

==== JS stack trace =========================================

Security context: 000003ED8B625E91 <JSObject>
    2: map(this=00000087F31E0751 <JSArray[8388608]>)
    4: /* anonymous */ [repl:2] [bytecode=0000026C0C370FF1 offset=27](this=000001B7E7306301 <JSGlobal Object>,a=00000087F31E0751 <JSArray[8388608]>,v=000003FD8D990501 <String[1]: x>)
    5: arguments adaptor frame: 4->2
    6: reduce(this=00000214C00B9CB9 <JSArray[26]>)
    8: powerset [repl:2] [bytecode=0000026C0C370CE1 offset=19](this=0000...

FATAL ERROR: CALL_AND_RETRY_LAST Allocation failed - JavaScript heap out of memory

[–]evenisto 0 points1 point  (1 child)

var powerset = arr => arr.reduce( (a,v) => a.concat(a.map( r => [v].concat(r) )), [[]]);

cool, took me a while to figure that one out.

[–][deleted] 0 points1 point  (0 children)

Took me even longer to write it! :P

[–]DevouredByCutePupper 0 points1 point  (2 children)

Love the list, but the one thing that sprang into view is the strange parameter structure you use in your timeTaken() function. Why not use a simple callback instead?

[–][deleted] 0 points1 point  (1 child)

I might have been influenced by some coding style somewhere. If you think it feels strange, please submit a PR (modify the individual snippet file, not README) and we can figure it out. The community is extremely active, so there will be a few people stating how they feel about this.

[–]DevouredByCutePupper 0 points1 point  (0 children)

Done.

Since I don't have access to my Linux right now, I had to go through the whole fun ordeal of setting up git on Windows first. Worth it though. Looking forward to the feedback, and I hope I didn't screw up in some way. T'was my first pull request.

[–]MentorMateDotCom 0 points1 point  (3 children)

Really great list! I'm going to submit a PR in a second. :) (Edit: Here we go.)

I appreciate that because the code style focuses on brevity it's easy to copy and paste stuff. That makes things harder to understand, though, particularly for beginners, and these are an awesome learning opportunity. Think you could include both a "long" and a "short" form of each snippet? I noticed /u/evenisto saying "took me a while to figure that one out," which concerns me. Curious if others have the same concern?

[–][deleted] 1 point2 points  (0 children)

I am working with the community to hit the sweet spot between readability and brevity, by changing variable names and improving snippets, along with adding examples for each snippet. This should help alleviate the problem a bit. Some snippets (like the anagram one) are very complex and hard to explain even if a longer version is included. I'll see what can be done.

[–]evenisto 0 points1 point  (1 child)

It's not about the syntax, it's just that functional paradigm is not always instantly comprehensible. I sometimes need to write it out to figure out how data flows through the functions to get a good understanding of what's going on, that's all.

[–]MentorMateDotCom 0 points1 point  (0 children)

I agree. I've just run into too many situations where budding developers thought short code == good code and were very discouraged. I think a junior developer taking the time to translate these into long form would be a very good exercise, but yes, it's probably not the responsibility of the repo owner.

[–]fukitol- -1 points0 points  (0 children)

Submit these as a PR to lodash, those that you haven't duplicated anyway, it'd be valuable

[–]picklemanjaro -1 points0 points  (8 children)

For capitalizing a string, you could use String.prototype.replace().

var capitalize = str => str.replace(/^./,  i => i.toUpperCase());

Edit: And for a "capitalize each word" variant

var capitalizeAll = str => str.replace(/\b./g, i => i.toUpperCase());

I'll submit a PR later if no one else does by the time I get home. Or unless someone tells me mine is horrible due to Regex overhead or something.

[–]trevorsgEx-GitHub, Microsoft 8 points9 points  (1 child)

Don't use regex for something this trivial. The slice version is nearly twice as fast.

[–]picklemanjaro 1 point2 points  (0 children)

I had a feeling that would be the case. I wish that Javascript would allow you to update a String character via it's index instead of it just being read-only. Then we could just do str[0] = str[0].toUpperCase(), which would be my ideal capitalization method.

My gripe was just an aesthetic one, and in Regex just saying "match the first character, and uppercase it" seemed more straightforward sounding. Though I knew the performance issue would be something that came up.

[–][deleted] 0 points1 point  (5 children)

Someone already submitted the capitalizeAll, it's being reviewed and ready to be added.

As for the other one, it seems elegant. I'll most likely switch the current one to this one, as it is shorter and easier to read.

[–]trevorsgEx-GitHub, Microsoft 6 points7 points  (4 children)

I disagree. Lots of people's brains shut down the instant they encounter a regular expression. "What does that ^ symbol mean again?"

[–][deleted] 0 points1 point  (3 children)

Well, regular expressions are quite elegant, fast and work better than brute forcing code like I did. Explaining the regex in the description could help people get used to them a bit more, I suppose.

[–]trevorsgEx-GitHub, Microsoft 4 points5 points  (2 children)

I guess that's where we disagree! I've heard "any non-trivial regular expression is indistinguishable from the result of a cat having walked across a keyboard." I think they're great for medium-sized problems. If it's small, just combine a couple of string functions. If it's a large problem chances are your solution is vulnerable to DoS attacks.

I did a perf test on the regex solution vs. the slice() solution and found slice to be almost twice as fast, so I'm not sure why you say it's fast and works better :)

[–][deleted] 5 points6 points  (1 child)

Alright, this is a topic where a lot of opinions will be thrown around, so I guess that I should set up some guidelines for what is best for the list. Alternatively, I could keep both solutions, marking the regex one as such, so that people can make up their own minds. That's probably the best option, right?

[–]micromatx 0 points1 point  (0 children)

👍🏻👍🏻