My Top 4 JavaScript No-No List
These types of posts have been done ad nauseam, but I'm putting together my own short list for a presentation so I thought I'd share.
They're not such a big deal in the grand scope of life, the universe and everything, in fact, these are far from the worst missteps you can take in programming.
However, seeing these same problems year after year drives me crazy. It's like fingernails on a chalkboard.
It makes my soul hurt.
So without further ado, I present to you: My Top 4 JavaScript No-No List
#4 Use semi-colons!
There are a couple of well-written articles that defend this lack of punctuation, and they argue their position well. However, I have yet to see a reason NOT to use semi-colons.
Just because you can nitpick the common arguments, blaming bad tools and bad programmers, doesn't mean that you shouldn't err on the side of caution.
I'm a firm believe in coding conventions, good un-abbreviated naming, and doing things like always including curly braces after your ifs. The same arguments apply to all, but I think it's worth the extra effort to provide that extra level of unabiguity.
If these efforts have prevented a single bug, then it's worth the extra keystroke.
#3 Cache your DOM calls!
It's impossible to talk about JavaScript, without mentioning jQuery nowadays.
It's probably just the extra typing, and I'm showing my age here, but I rarely saw repeated document.getElementById-ing.I don't know what it is about the beloved library that make people think it's okay to keep $(searching) for the same element.
I cleaned up a function recently that queried the same DOM element 8 times in a single function. That's 8 times checking the search and 8 times the memory allocation every time that functions called, when only one was needed!
Here's what I'm on about:
Do This:
var anything = $('#id');
anything.likeThis();
Or Do This:
$('#id').likeThis().andLikeThat();
Just DON'T DO THIS!
$('#id').likeThis();
$('#id').andLikeThat();
$('#id').andLikeThis();
#2 Put it in a file!
- Files are easily minified, saving bandwidth and time
- Files get cached, saving bandwidth and time
- Files make re-use easier
- Files mean less noise in your html templates
- Files keep your behaviors code out of your markup
I'm having a hard time coming up with a con here.
If you need to set server-side variables in your JavaScript then you're probably doing it wrong. If you need your js in-line then again you're probably doing it wrong.
Read more about unobtrusive javascript here, and take a few minutes to consider alternative approaches next time you think about breaking this rule.
#1 Avoid Globals!
You knew this was coming, didn't you.
VAR YOUR VARIABLES
If you don't var your variables, then you're writing to the global scope. This means your variables can be written over by anyone else who's foolish enough to write to the global scope.
You may think that this doesn't matter. You may think that that your scripts will be the exception, and that they will live and operate in isolation for their enter lifetime. But can you really guarantee that?
And once again, ask yourself what is the downside?
In addition to being safer and promoting encapsulation, it also helps the maintainers narrow down the scope of there debugging. That's a pretty big pro.
I've spent countless hours over the last 10 years tracking down problems caused by overwritten globals, and it's a problem that's easily avoided with just three little letters.
In Conclusion
If you take a step back you'll see that there's a common theme here, and it applies to any language: Don't be lazy.
The time you save cutting these little corners is next to negligible, and often lead to really annoying problems down the road. If you're a professional developer, than you owe it to yourself to take the time to do it right. There are enough problems to contend with, without tripping over our own feet.
PS: Now that I'm off my high horse, I should admit that I've learned all of these lessons the hard way, and that I'm still working at it.
Project Euler : Problem 39 in Ruby
I had an easy time with this one, which makes me feel a lot better about all the ones I had problems with!
No fancy-pants recursion or math short-cuts here, just a straight forward logic problem. The only "trick" here is to realize that since a <e; b < c, we only need to check values of a and b up to 499.
I'm sure you could whittle that number down by crunching the numbers, but it's good enough for me!
For which value of p 1000, is the number of solutions maximised?
counts = {}
counts.default = 0
(1..499).each do |a|
(a..499).each do |b|
break if a + b > 500
c = Math.sqrt(a**2 + b**2)
next unless c.denominator == 1
counts[a + b + c] += 1
end
end
sorted = counts.sort { |a, b| a[1] <=> b[1] }
puts sorted.last[0]
The Best Programming Music
I listen to a lot of music at work. All day, every day.
It helps smooth frustrations, keeps me awake, and provides "color" for my day. I want my office to feel like a 1960's Sci-Fi movie!
Most importantly, the music helps me "flow" by drowning out the regular office clatter and bang-clangery.
Admittedly, I tend to "burn out" early on music, but 2,000+ hours of work/year will eventually tire even the most stalwart listener and extensive collection. Especially since a lot of the music I like "in real life" doesn't mesh well with concentrating. I usually find lyrics to be too distracting.
Since audiobooks and podcasts have taken over my ipod, I do almost all of my music listening at work. This has introduced a strange and large gap between the music that I used to like and the music I actually listen to.
Although I love it, my office is a no Kanye zone!
Since I require so much "background" music, services like and Pandora are perfect fit for me. I'm constantly tweaking my stations, but here's my current fave for work:
My favorite Pandora Station:
Programming Music: Boards of Mercury Circles
And here's a few youtubes of songs you might hear on that station:
Project Euler : Problem 38 in Ruby
40 problems down, 10 more till level 2!
The real trick here is to cut down on the numbers you check. Since the problem gives you 918273645 as an example we know the answer must be greater than or equal to it...meaning we only need to check digits that start with 9!
I don't actually do it because I couldn't figure out an elegant way to do, but it runs in just a few milliseconds so it's fast enough in my book.
Another important factor to note is that you only need to check numbers up to 9_876 since this is the first 'half' of the largest pandigital possible.
Those two tricks will cut down the calculations you need to run to just a few thousand.
What is the largest 1 to 9 pandigital 9-digit number that can be formed as the concatenated product of an integer with (1,2, ... , n) where n 1?
def get_pandigital? n
nums = []
(1..9).each do |digit|
nums += (n * digit).to_s.split ''
return 0 if nums.size != nums.uniq.size || nums.include?('0')
return nums.join('').to_i if nums.size == 9
end
end
solution = 0
(9..9_876).each do |n|
# could do better by only looking at 9's!
result = get_pandigital? n
if result > solution
solution = result
end
end
puts solution
Check out all of my solutions on bitbucket!
Project Euler: Problem 37 in Ruby
It's been a while since I've done one of these, so I was afraid of being rusty but it worked out alright. I used the generator I made a while back to create the primes (pre-filled to the example given in the project) and used procs to take care of the truncation.
BAM!
The number 3797 has an interesting property. Being prime itself, it is possible to continuously remove digits from left to right, and remain prime at each stage: 3797, 797, 97, and 7. Similarly we can work from right to left: 3797, 379, 37, and 3.
Find the sum of the only eleven primes that are both truncatable from left to right and right to left.
load 'prime_generator.rb'
def prime? n, truncate
return false if !$primer.is_prime?(n)
return true if n < 10
prime? truncate.call(n), truncate
end
left = Proc.new { |n| n / 10 }
right = Proc.new { |n| n % 10**Math.log10(n).to_i }
$primer = Prime_Generator.new 3_797
n, sum, found = 0, 0, 0
while found < 11 do
if (n += 1) > 10 && prime?(n, left) && prime?(n, right)
found += 1
sum += n
end
end
puts sum
Also, I've finally moved my project euler solutions over to bitbucket. Long live Mercurial!
































