melreams.com

Nerrrrd

Context!

a railway bridge supported by brick arches surrounded by lush green jungle
Unrelated image from pexels.com to make this post look nicer in social media shares.

So I was browsing workplace.stackexchange.com questions late one night, as you do, and came across an interesting one: How to explain business priorities to a programmer.

That one didn’t go at all the way I thought from the title. It turns out the business priorities actually did make sense (the business had this wild idea that queries, even especially complicated ones, should take less than 4 hours to run) and the programmer was being unreasonably rigid in following “best practices”.

But weirdly, one of the answers said that both parties were wrong – that the programmer shouldn’t have been so attached to having nice looking code and the manager shouldn’t have insisted on using an anti-pattern. What? The anti-pattern (using raw SQL instead of the ORM) improved performance by multiple orders of magnitude! If performance matters at all, you cannot possibly tell me that massively improving performance was the wrong thing to do.

Okay, there is some nuance there :) If your ORM performs that badly it’s likely not configured right for your situation, so it might be better in the long term to fix your config than to keep writing custom SQL for every query that’s the least bit complicated. On the other hand, if you don’t have an expert handy who can tune your ORM config, it might be easier to ditch it, at least for the more complicated queries, and just write some SQL. Or hey, how about a compromise? Use a stored procedure, that’s what they’re for! If it’s a query you run a lot, it might even make sense to make a view for it.

No matter what you end up doing, it’s still not wrong to use a supposed “anti-pattern” if you have a good reason to do it. It’s the context that makes something a bad idea, even the best idea can turn bad if you use it the wrong way. The only way to know whether your “anti-pattern” is actually a bad idea for your particular situation is…. to look at your particular situation! You can’t just say something is an anti-pattern without knowing what the person using that anti-pattern is trying to accomplish.

Let’s look at another datebasey example. It’s generally considered a bad idea to denormalize your database, every database design course will tell you so. Normalizing your database ensures all of your data is always right by isolating everything that can change independently. Since you don’t usually bother to keep data at all if you don’t care if it’s all accurate, you almost always want your data nicely normalized.

But sometimes correctness isn’t the absolute most important thing. Let’s take browser or mobile games, for instance. If your game takes too long to load, your players will just go do something else and they might not ever come back. It’s much more important to be fast than it is to be perfect if you want to make money on a game like that. And if something does go wrong and a player gets mad because their data didn’t get saved correctly, you can just give them game currency until they’re happy again.

In a situation where performance is more important than correctness, normalization is the anti-pattern. Like I said, it’s all about context!

To be clear, there are some things that are just a terrible idea no matter what you’re doing. I don’t care how clever you think you are, your variable names need to make sense. And no matter how well it performs, if your system is so confusing than no one can make updates, then it’s a bad system. But for the most part whether or not something is an anti-pattern is about what you’re trying to accomplish more than it’s about the “anti-pattern” itself.

Everybody likes code that makes sense to them, and everybody likes to feel like they’re doing things the right way, but rigidly following “best practices” just isn’t good enough. If it doesn’t help you achieve your greater goals for your application (ie not just gold-plating your code, but providing value to your users or customers), it’s just not a good idea no matter how many experts call it a best practice.

And yes, that means you can’t know if your code is good or bad without knowing exactly what you’re trying to do. Welcome to professional programming!

Be a better programmer while still having a life: part 11

an alarm clock with a weathered, rusty face sits on a rustic wooden table
Loosely related image from pexels.com to make this post look nicer in social media shares.

Don’t be a time thief. More precisely, if a decision has been made let it stay made.

This tip won’t necessarily change your personal output a whole lot, although you will have more time for your own work if you don’t waste it rehashing old decisions, but it will be fantastic for your team’s productivity. Being a better programmer isn’t just about how much you personally get done, it’s also about how much your whole team gets done. If you make your team better then congrats, you’re a better developer!

You will have to deal with decisions you don’t like as a developer. I’m not saying that’s a good time, but that’s not just life as a developer, it’s life in general. You can either accept those decisions like a grownup, or you can waste everyone’s time by fighting the same battles over and over.

Now, if something has substantially changed, like a new tool has been released or there has been an announcement that an open source library is no longer being actively developed, then it may make sense to reopen a closed discussion. But if you just don’t like the decision, you’re wasting everyone’s time. Even if you are technically right it’s generally faster to rework your codebase to recover from a decision that didn’t pan out than to have the same meeting over and over. It’s not just about the single decision, it’s about how you use your time.

It’s also about morale. It’s incredibly frustrating when you have meeting after meeting and finally decide something, only to have someone drag it all back up again a few weeks later. What was the point of all the earlier meetings if a decision that’s been made doesn’t stay made? If you want people to stop bothering to share their opinions, that’s the way to do it. Like I said last time, you have to be open to the idea that you could be wrong. You need your team’s ideas to make the best decision you can, and you can’t possibly get anyone’s real ideas when you convince them that it doesn’t matter what they say.

Arguing about things that are purely a matter of opinion is time-theft too. Curly brace on the same line as the method declaration vs the next line? tabs vs spaces? line width? No professionals bother to argue about that at work (the bar is a different story, however :) ), we pick a coding standard, set our IDEs to autoformat our code correctly and move on with our lives. Some arguments simply are not worth the time it takes to have them.

Speaking of arguments that have been had over and over and are a profound waste of everyone’s time, biology simply does not and never has explained the lack of women in computer science. We seem to drag this argument back up every few years in tech and every time it’s as foolish as it was last time. Google bro is simply the latest to waste thousands of hours of everyone’s time with ideas that have been debunked over and over. A grownup, not to mention a competent developer, would never have wasted everyone’s time with an argument that’s been hashed out dozens if not hundreds of times already. You simply can’t have someone like that on your team if you ever want to get anything done – even a competent developer, which Google bro certainly is not, couldn’t offset the collective productivity lost to rehashing well understood decisions over and over.

It’s perfectly normal to want to undo a decision you don’t like, just like it’s perfectly normal to want to stay in bed on a cold, wet morning and it’s perfectly normal to want to buy lunch and skip packing one. Wanting, however, is different from doing if you’re a grownup and you just can’t be a good developer without being a grownup. Even a lone hobbyist faces frustration and disappointment, you can either let those stop you in your tracks or you can set them down and make yourself useful.

Be a better programmer while still having a life: part 10

a metal framework tower holding up power lines is silhouetted against a dark sky that appears to be photoshopped because it is purple
Unrelated image from pexels.com to make this post look nicer in social media shares.

A little bit of self-doubt is good for you! That might sound weird but hear me out. Doubting yourself just enough to accept the fact that you don’t know everything and will be wrong sometimes is incredibly useful in software development. So many projects have died when the thing that everyone assumed would be easy (or at least doable) turned out not to be. If you can accept that you could be wrong and do a little double checking, you can save yourself so much pain.

While we’re on the subject, if you ever hear the words “it’s done, we just need to integrate it” you should be very very afraid. Not only is the thing not done, but it’s not going to be done any time soon. I admit I’m generalizing from a small sample here, but I’ve never seen the assumption that integrating a new feature will be easy turn out to be accurate.

In general, if you’ve never used that API before, don’t assume it will be easy. Read the docs really thoroughly too – just because it sounds like that API does what you need doesn’t mean it actually does. I’ve been burned by that before and you probably will be too. Same thing for libraries you haven’t used before. Just because you think a library should work a certain way doesn’t mean it actually does. In case you weren’t already worried enough, don’t forget that sometimes the docs are outdated, missing, or just plain bad, too. There’s more than one reason building a very simple proof of concept first is such a good idea.

Like I said earlier, don’t assume you understand the problem either. Talk to people until you’re sure you understand why that feature should exist, not just what it should do. Talk to your team lead, talk to other departments, ideally talk to someone who is actually going to use the thing (I know this isn’t feasible for everyone but it’s really great if you can manage it). The assumption that you’re right about what people need kills projects too. You would think that would be an obvious thing to check, but judging by the horror stories in the news about massive government projects that turn out not to do what the front line staff actually need, it’s not obvious at all.

Seriously, I can’t stress enough how dangerous assumptions are to projects. That’s how projects end up months if not years late and massively over budget if they get delivered at all. Refusing to admit you could ever be wrong kills projects too. The real problem, underneath the assumption that integrating that API will be easy to integrate, is the assumption that you’re right and don’t need to check.

In addition to killing projects, failing to question your assumptions can also lead you to make a complete fool of yourself, a la google bro. If he had questioned any of his assumptions, if he could have faced the possibility he could ever be wrong about anything at any time ever, he would be a far better engineer. As it is he clearly can’t be trusted not to make wild assumptions that will doom his projects, and if you can’t trust someone to check their own assumptions you simply can’t trust them to work as a senior engineer. One simple definition of engineering levels is that junior developers need adult supervision, intermediate developers can work on their own, and senior developers are adult supervision. If you can’t bring yourself to accept that you could ever be wrong about anything, then you can’t competently supervise anyone.

Too much self doubt is obviously completely unproductive, and you can never know everything there is to know about your project before you build it, but a little self doubt is enormously useful and tremendously underrated. In tech we seem to place so much emphasis on always being perfectly sure of yourself but not only is that an unreasonable goal, it’s not even useful. What’s useful is understanding that the most brilliant writers still need editors, and the most brilliant programmers still need input from their teams. Nobody is right absolutely all of the time, the word for people who think they are is “delusional.”

Admit you could be wrong and you’ll end up with the right answer a lot more often.

Be a better programmer while still having a life: part 9

brown wooden wheel on an old cart with fallen leaves around it on the ground.
Vaguely related image from pexels.com to make this post look nicer in social media shares.

Don’t reinvent the wheel! I’ve touched on this before, but it definitely merits its own post.

A huge part of becoming a better developer is understanding when you don’t need to write new code to solve a problem. The more code you write, the more code you have to maintain, the more chances you have to screw it up, and the more time it takes to write it. So before you write new code, see if there’s a library, a plugin, a product, a design pattern, or a best practice that solves your problem. At least see if anyone wrote an article or blog post about a similar problem and learn from what they did.

To be fair, sometimes what you need really isn’t well served by an existing trustworthy product or library and you do need to write your own custom code, but that needs to be an informed choice, not a reflex.

What I think makes a product trustworthy is active development and a large userbase. The main advantages of using a library instead of writing your own code is that you don’t have to update it and that most of the bugs have been worked out already because so many people use it. By all means use a small library that isn’t maintained if it’s convenient and not a core part of your project, but for the love of god don’t depend on a framework/database/core part of your project that isn’t actively maintained and/or doesn’t have any users. That will just end in tears.

You also don’t want to import a library for every little thing, the more libraries you import the more bloated your project becomes and the more chances you have to run into a bug in one of them (and let’s not forget the left-pad debacle), but for stuff that would take more than a few hours to write, see if somebody else already wrote it.

For example, writing your own regex to validate email addresses is almost certainly a waste of time. Are you really going to write a better validator than the Apache Commons EmailValidator? No, you’re not. And do you want to have to maintain it forever even if you do write a great validator? No, you don’t. So use the library and move on with your day.

Yes, writing code is way more fun than integrating a library, but when you’re at work your job is to get results. If writing your own code gets the best result, do that, but if integrating a library gets the best result, do that instead. Of course, to understand what gets the best results, be it a library, a whole product, an API, a design pattern or whatever else, that means you have to understand what’s out there.

As a bit of an aside, that’s why the Google bro is an incompetent engineer – his ridiculous screed shows he either didn’t read or didn’t understand any of the existing research about personality differences between men and women (spoiler: there aren’t any statistically significant ones). While junior engineers get a pass on not searching for or not understanding existing libraries, senior engineers do not. If you can’t Google (see what I did there :D) existing research or existing libraries, you simply are not operating at a senior engineer level.

Sometimes it is useful to reinvent the wheel – modern wheels with inner tubes and shock absorbers make riding in a modern car a lot more comfortable than riding in the first cars with their solid wheels (Google bro’s wheel, on the other hand, is square and the axel is off center, which is just embarrassing). If you can’t do better than existing wheels, just use what’s already out there and save yourself some time.

Ironically, admitting that you aren’t the greatest developer who ever lived makes you a better developer. Accepting that actively maintained, well-used libraries are often better than what you would write on your own not only saves you a lot of time, but also makes your final product better.

What’s the big deal about years of experience in a language?

A young cow in a sunny green field looks toward the camera
Unrelated image from pexels.com to make this post look nicer in social media shares.

A while ago I was wasting time on reddit, as you do, and came across an interesting question: “why do employers and just about everyone else make a big deal about language-specific positions and “what language should I learn”, etc.?” The greater context there was that the asker had a pretty easy time picking up new object oriented languages once they got a good handle on one of them, so they were confused about why people seem to think x years of experience in language y were so important.

I have mixed feelings about job postings that require a certain number of years of experience in any particular language. If you understand programming concepts (from low level stuff to how ifs and loops work to higher level stuff like how to keep your core business logic separate from presentation code) then yes, it’s pretty easy to apply those in whatever programming language you need to.

As a bit of an aside I think a lot of job postings are more of a wildest dreams wishlist than a useful description of what’s actually necessary to do the job from day to day. In the context of this particular question, I have a strong suspicion that when most job postings say the applicant needs “5 years of experience with Java” what they actually need is someone who knows Java and has 2-5 years of programming experience.

That said, while most programming concepts are transferable (especially if you’re using languages with broadly similar syntax), you really are more productive with a language you already know well, especially if you don’t have much programming experience. There are weird quirks of languages you may not run into at all until you’ve been working with them for a while, too.

For example, did you know in Java String.substring() used to return a “view” of the original string, not a completely separate string? And that since Java 1.7 update 6 it returns a completely separate string? Yes, that seems really minor but it can cause some weird weird bugs if you change the original string thinking it’s completely separate from the substring. And because stuff like that doesn’t look wrong, it can be absolutely miserable to track down.

Just because I technically can code in languages other than Java doesn’t mean I can do it quickly. When I need to do any front end work I spend a lot of time looking things up because I don’t remember the exact parameters basic string operations take in Javascript. If I had to write Javascript all the time I would start remembering those details, but that’s with a foundation of years of programming experience to start from. If you’re a new dev who just graduated from college/university/bootcamp, you’re going to have a harder time learning a new language because you’re also going to be learning professional programming at the same time.

Which language you learn first also makes a big difference in how hard of a time you have learning to code. In general I think you should start with whatever language lets you build stuff you’re excited about, but I don’t want to pretend all languages are equally beginner friendly either. C and C++ are good for many things but they are not your friends :) Python and Ruby are easier to pick up because they take care of fiddly details like memory management for you, and Javascript can be a good first language because you don’t need any special programs like IDEs or compilers at all, you can write it in notepad and run it in your browser.

So given all of that, why do (some) employers make such a big deal about language specific positions? Because if you don’t already understand programming really well, you need some way to find people who have a decent chance of succeeding in the position you want to fill. Sadly, not all job postings are written by people who understand the day to day work so it’s not unusual to end end up with some poor HR person’s best guess at what’s needed.

“5 years of Java experience” can also be a pretty decent proxy for “actually likes working with Java and won’t ditch us in a year to work in [cool new language of the week]”. Some languages are just not considered cool and plenty of people have a perfectly legitimate dislike of the amount of boilerplate you have to write to make Java do much of anything, so it makes sense to look for people who are willing to work with your tech stack for the long term (or at least the longer than one year term).

Readers, what do you think of stuff like “must have 5 years of Java experience” in job postings?

What does being an experienced developer actually mean?

Unrelated image from pexels.com to make this post look nicer in social media shares.

I was poking around in /r/javahelp, saw a question about something I haven’t personally done, and found what I strongly suspect was the answer right away.  I try to explain how I found the answer when I answer questions like that because “oh it’s _____” isn’t really that helpful in the long term. I mean, what is the question asker supposed to do next time if I’m busy or sick or on vacation?

But how do you explain “well obviously that’s a_____ problem”? I can explain that I googled a thing and didn’t get very helpful results so I googled another thing and found what I needed, but not how I knew what to search for in the first place.

The closest I can come to explaining how I recognize problems is a term I recently learned from Katrina Owen‘s talk Cultivating Instinct. That term is perceptual learning, which according to Wikipedia is:

learning better perception skills such as differentiating two musical tones from one another or categorizations of spatial and temporal patterns relevant to real-world expertise as in reading, seeing relations among chess pieces, knowing whether or not an X-ray image shows a tumor.

After you’ve worked with enough code and seen enough different kinds of problems, you just kind of know what the answer is (or at least a few things it could be) when you see a new problem. And that, finally, is what being an experienced programmer really means. It’s not about some magical level of skill or about instantly knowing the perfect solution for every problem or even finally feeling like you know what you’re doing, it’s just about having seen enough problems that you end up with a library of them in your head.

I can’t tell you how long that will take but on the upside I can tell you it will definitely happen if you just keep coding. Okay, there are people with “ten years of experience” who really just have one year ten times, but if you care enough about programming to bother reading my blog, you’re not one of them.

Another part of being an experienced programmer is that once you feel confident about getting your code to do what you wanted, you sort of move up a level and start worrying about whether it’s a good idea to do it that way. That’s where people with one year of experience ten times really fall down, they can make things work but can’t make them maintainable. Getting to the point where you worry about the right way to do things takes a little more deliberate effort, but the most important step is just to care about whether it’s possible to change your code.

Once you’re past struggling to get your for loops to work and once you’re past feeling totally overwhelmed by starting a new project, it’s really tempting to think that you’re done, you’re a “real” programmer now and there’s nothing else you need to learn. But if you stop there, not only will you never be a very good programmer, but more importantly you’ll miss out on one of my favourite parts of programming, which is figuring out how to design things so you won’t curse your name in six months when you need to change them. For me that’s way more fun than Strings and Arrays.

All this is to say that if you’re a beginner programmer and you see a job posting looking for developers with x years of experience, all they really want is someone who can reliably get things to work (not necessarily immediately) and who knows a bad idea when they see one. If you can do that, go ahead and apply. It’s not unusual for job postings to be more of a wishlist than a list of what the job actually requires, anyway :)

Resume advice

Unrelated image from pexels.com to make this post look nicer in social media shares.

The academic year is ending pretty soon and students are probably starting to look for co-op jobs, so hey, why not throw some unsolicited resume advice at people?

First a quick disclaimer, I help review resumes now and then but I don’t have a huge amount of experience with it. Some of the stuff I’m going to tell you is stuff I’m really sure I’m right about, and some of it is just my opinion.

My first piece of advice, and the one I’m the most sure about, is proofreading. Proofread your resume! Put it away for a little while (at least a few days), and proofread it again! Get a friend to proofread it! Get your parents to proofread it! Go to your school’s career center and get them to proofread it! Wow, the word proofread looks really weird when you use it that much :)

But seriously, proofread! Why am I harping on that one so much? Because a resume with mistakes on it shows you aren’t good at fiddly little details. That’s a serious problem because programming is fiddly little details. Compilers and IDEs and syntax highlighting text editors can help you catch a lot of bugs, but they can’t catch logic errors for you. To find and fix logic errors, you have to pay really close attention to the code and keep track of every little detail. If your resume has mistakes, that makes me very worried that you’re going to struggle with programming in general and logic errors in particular and honestly, that’s going to make me very likely to set your resume aside. I say “very likely” because it is possible that if you had some really great projects on your resume I would still consider your resume, but you know, it’s a lot easier just to proofread the hell out of your resume :)

On top of making me worried about your ability to program, having mistakes on your resume just looks sloppy. That’s really not the first impression you want to make on a potential employer. In school it’s not as big of a deal if you lose a couple of points for having a typo or an autocorrect fail, but when you’re applying for a job that’s very likely to take your resume out of consideration entirely.

My next piece of advice is detail. Almost no one has too much detail on their resume, you basically can’t go wrong if you add more detail about exactly what you did, especially on projects you did as part of a team. When I’m looking at a resume, I want to know what you did. If you were involved in every part of the project, just say that instead of letting me wonder what you actually did. If you just did, say, the back end part of the project, say that! If I’m looking for a back end dev, I want to know if you have back end experience.

This one’s a little more subjective, but personally objectives on resumes take up space that could be used to tell me something more interesting. I mean, I know you want to work on software, it would be pretty dumb to apply for a dev job (co-op or otherwise) if you didn’t. That said, I’ve heard from other people that objectives make it easier to keep track of which position someone is actually applying for, which can be really handy if you don’t use an applicant tracking system and have a pile of resumes you’ve printed out. Basically, go ahead and include an objective if you want to, but don’t feel that you have to just because your teacher said so.

Job history is a tough one for students especially, I have two pieces of advice for you there. One, it is totally okay to have a projects section on your resume if you don’t have a lot of relevant work experience. Heck, even if you do have a lot of relevant work experience, if you have projects you’re proud of have a project section on your resume! Opinions differ on this one, but I think it’s perfectly fine to include school projects on your resume. What else are you supposed to do if you’re a student?

Two, you do not have to list every crummy summer job you’ve ever had. Especially if you took breaks from school to work to pay for your next semester, you do not have to use up half a page listing every retail/hospitality/whatever job you’ve ever had. If you took breaks from school to work it’s not a bad idea to explain that in your cover letter, but I’d much rather hear about cool projects from your classes than about stint #4 at $FastFoodPlace on your resume.

Readers, do you have any advice for students or anyone who doesn’t have years of dev experience to put on their resumes?

Be a better programmer while still having a life: part 7

Unrelated image from pexels.com to make this post look nicer in social media shares.

Back in part 1 I talked about how important it is to make sure you understand the problem you’re trying to solve. Today I want to expand on that because there’s much more to problem solving. Having a great understanding of the problem you’re trying to solve is great, but it’s not always enough. Sometimes you’re wrong about what the problem actually is. No matter how well you understand the problem you think you have, it’s not going to do you much good if you’re trying to solve the wrong problem.

Telling people to make sure they’re solving the right problem is all well and good, but an actual example always makes things a lot clearer. Conveniently enough, I saw a great example of this problem on workplace.stackexchange.com the other day. To summarize the question quickly in case it disappears someday, the questioner wants to know if there are any alternatives to doing code reviews because not everyone likes doing code reviews. To quote part of the question:

Are there any alternative processes that could replace the code review for the goal of improving the code quality? Would it be possible to have something else instead of this process? While review may be required where software bugs kill humans, could some weaker method be sufficient where the situation is far from that critical?

An edit clarified that the reason the question asker is looking for an alternative to code reviews is because people in their organization use them to play power games and prevent other team members from contributing to the project. At this point you may be developing a theory about why I think “what can we do instead of code reviews?” is the wrong question :)

This particular question did happen to contain a great clue – there’s really no substitute for reviewing your code if you want to improve it. That’s kind of like saying you want to be a better writer but you don’t want anyone to proofread your work. When your solution goes directly against your stated goal, there’s almost certainly a deeper problem. Sometimes that problem is fixable and sometimes it’s not, but there’s definitely something there you need to look into.

Given that the reason the question asker wants to find an alternative to code reviews is because team members are using them to jerk their colleagues around, I don’t think it’s too much of a leap to the conclusion that the real problem is that people are being jerks and playing power games when they’re supposed to be working as a team and that trying to avoid code reviews is just a workaround for a serious culture problem.

To be clear I don’t blame the question asker for trying to solve the wrong problem. I’m assuming they aren’t a manager and/or don’t have the authority to tell the power game players to knock that shit off and start acting like grownups, so finding some way to avoid code reviews without completely ignoring code quality is about all they can do to work around the real problem. But if you’re going to do that, and sometimes finding a workaround/bandaid solution is the only thing you actually can do, I still think it’s important to be honest with yourself that what you’re doing is putting a bandaid on the real problem. If you forget that, you’re going to get a nasty surprise later when it turns out the real problem has popped up again in a different form.

To keep harping on the code review example, just because you’ve removed one avenue for for jerks to play power games doesn’t mean everyone is going to start playing nice. If you do retrospectives or post-mortems of any sort, jerks are going to use those to throw their colleagues under the bus and/or to take credit for their work. Whatever system you use to assign work, jerks will try to abuse it to keep the interesting/fun/easy/politically valuable tasks for themselves and leave the dregs for someone else. And no matter what you try to do to control bad behaviour in your development process, you can’t prevent someone malicious from going to lunch with their dev manager buddy and complaining that that one feature sales keeps pushing for has to be postponed again because so-and-so just isn’t contributing anything (of course they’ll leave out the fact that the malicious dev won’t approve any of their pull requests), they’re such a drain on the team.

This particular problem is especially difficult to actually solve because the real solution is for management to do their jobs and enforce consequences for sabotaging team mates and otherwise refusing to act like a professional. Making anyone, especially someone who outranks you, do their job is never an easy task, so I completely sympathize with the urge to “fix” the symptom rather than the root cause. Some problems are simply above your pay grade, others may be so complicated or expensive to fix that it’s better for the business to keep working around them.

In other cases, fixing the root cause of the problem actually is doable and cheaper or more efficient than keeping a clumsy workaround. Even then, you can’t fix the root problem without knowing what it is, so keep asking why until you get down to a bedrock answer like “Because that’s how this company makes money.”

 

Link of the day

Julia Evans has a great guide to asking good questions, you should read it :) Asking good questions is such a useful skill, I wish programming education spent more time on it.

Getting really good at asking questions is also a great hack for looking like a better developer (it’ll also help you actually become better, but in the short term it’s a good hack). When you ask a bad question, like “My code isn’t working, can you help me?” people have to wonder what you’ve tried already or if you tried at all before giving up and asking someone else. If you ask the exact same question with more detail, especially about what you tried already, like “I’m trying to send an email but I’m getting an error message I don’t understand. I tried googling it but I got a bunch of different answers and I don’t know which one applies to my problem. Can you help me sort through them?” then it’s obvious that not only did you not immediately give up, but you also respect your answerer’s time enough to make it as easy as possible for them to help you. Telling them what you’ve tried already means they can skip suggesting things you already did, and asking a specific question means they don’t have to do the work of figuring out what the question actually is before they can even start thinking about how to answer it.

People love it when you make things easier for them, and when you show them you’ve put some effort into doing so, they’ll think you’re a better programmer than the person who makes getting the real question out of them like pulling teeth even if both of you are around the same skill level. That’s the hack part :) The becoming a better programmer part is that stating a question really clearly (yay rubber ducks!) and listing everything you’ve tried already may trigger that flash of insight about what you haven’t tried but should or what assumption you made that could be wrong. If you get into the habit of reflecting on what you’re doing, you’ll learn a lot faster than someome who sits around and waits for help.

Do you have to be good at math to be a programmer?

Slightly related image from pexels.com to make this post look nicer in social media shares.

One of the most common misconceptions I’ve heard about programming is that you have to be a math whiz to be a good programmer. I’ve mentioned this before but I want to attack that particular stereotype more directly.

It is true that there are similarities between math and programming – programming uses some math terms like function and variable, it’ll be a lot easier to get things onto the screen if you understand coordinate systems, and of course to do math or programming you spend a lot of time manipulating symbols and thinking abstractly, but you know, programming is also a lot like language. I mean, they call them programming languages for a reason. To quote Hal Abelson, Jerry Sussman and Julie Sussman’s book Structure and Interpretation of Computer Programs:

First, we want to establish the idea that a computer language is not just a way of getting a computer to perform operations but rather that it is a novel formal medium for expressing ideas about methodology. Thus, programs must be written for people to read, and only incidentally for machines to execute.

Programming is fundamentally about communication. Not only are you communicating with the machine, you’re communicating with your future self, the rest of your team, and potentially other teams if you end up working for a large enough company. And that’s just when you’re writing code! You’ve also got to make sure you’re building the right thing and let other people who are waiting for that thing know how it’s going. You know what’s great practice for communication? That’s right, English classes! Sarah Mei has a great blog post about the same point I’m trying to make in this one, here’s an especially interesting quote:

The students I saw – all adults – came from a wide range of backgrounds. People with a math background did fine, of course, but people with a heavy language background often did better.

Nobody seems to have an official study on this, but I think there’s something there. Language requires just as much abstract thought as math does, with the added benefit (to your communication skills) of failing your classes if you can’t make yourself understood to anyone else. As a bit of an aside, the biggest problems I’ve run into at work have never been problems of pure programming skill (although those ones do suck a lot), they’ve been communication problems with team members, other teams, management, other departments entirely and other offices.

And to stick another nail in the coffin of the idea that programming is math, I’ve been a developer for ten years now and the most complicated math I’ve ever had to do at work is stuff like “if I have a div that’s x pixels wide and y pixels tall and I want it centered inside another div that’s a pixels wide and b pixels tall, what should my margins be?” I used to believe that programming was math, and some programming is certainly math heavy, but it’s hard to argue with the lack of math in my day to day job over ten years and four companies.

So given that programming is not math, why do so many people think it is? I’m going to quote Sarah again because she already said it really well:

When programming was just getting started, early in the last century, we used it to solve highly mathematical problems like calculating missile trajectories and decrypting secret messages. At that point, you had to be good at math to even approach programming. Tools, such as programming languages, were designed specifically to solve mathematical problems, because those were the ones we thought it was worth spending money on. Computers were for doing math.

I think another issue is the way we teach programming (credit where it’s due, I stole that idea directly from a comment on Sarah’s post). Computers are great at doing boring and tedious calculations, plus it’s easy to tell them how to do it, so why not start teaching programming by having students make the computer calculate something for them? It makes it really easy for the students to check their work too – assuming they’re able to do the math problem themselves, they can easily check if the computer got the same answer.

That assumption can be a real problem, though. If you can’t do the math problem or don’t care about the math problem, you end up effectively shut out of programming, something you could very well be great at, because of something that has next to nothing to do with the actual job of software development.

If you can do basic arithmetic and deal with the concept of variables, congrats, you can be a programmer! That is literally all the math you actually need!