by Sam Ollason
Lessons I’ve learned from 2.5 years of Software Engineering
I’ve been programming on and off since I was 16, but it’s only in the last of 2.5 years that it’s fair to say I’ve been working as a software engineer. In that time I have worked in a global team for a large and established investment bank and I am currently the Lead Developer for a revolutionary actuarial software start-up. I have worked with lots of exciting technologies and I have learnt an enormous amount.
Here are a some of the key lessons and tips, particularly from my earlier years, that I wish someone had shared with me when I first started. I hope they help you.
It doesn’t have to be perfect — just ‘good enough’
We software engineers love building things and naturally we become attached to what we build.
If you aren’t a software engineer, imagine building a brand new car from scratch. Imagine spending months or years creating a car using just your brainpower, hard work, determination and team spirit. It was planned to be, and is, faster or better looking or easier to use than an alternative car. Of course you are going to love what you build and be attached!
Because of this attachment, it is easy to continue pouring time and energy into a project to continue ‘perfecting’ it. In fact, it is sometimes very hard to not do this!
Lesson: Usually, you aren’t trying to write the best, most perfect solution to a problem — you are trying to add value to your team and your stakeholders. That means solving the problem in the time limits you have, making sure that your code style fits in with the wider codebase, and that it is tested and works properly.
Tip: Understand when a solution is ‘good enough’. When I am gathering requirements for a project I make sure to ask exactly what are their expectations and what their definition of ‘good enough’ is. More reading: the MoSCoW prioritisation technique.
Tip: Also, bear in mind that this may change throughout the project, so it is important to be in regular communication about where your focus is and where your stakeholders want your focus to be. This will make you a better developer … and a less-stressed human!
No-one knows everything
It’s easy to think that everyone knows more than you and you aren’t good enough to contribute. This a form of ‘imposter syndrome’ and lots has been written about it.
My experience: When I first started in my job at the bank I remember sitting in a room full of my team thinking “I don’t know enough yet to call myself a ‘software engineer’ yet”. I remember not having the confidence to attach this title, and what it represents, to myself.
She explained to me, without any form of embarrassment, that she actually didn’t know that much about modern front-end development and that she hadn’t followed the conversation earlier at all. I was amazed that there was something about software development that I knew (and knew really well) that she didn’t know. I was really pleased to teach her what I knew and answer her questions.
Lesson: That was the first time I properly appreciated that no one knows everything in our industry. It is so vast and ever-changing. So don’t worry if you don’t know everything, because no one does. Instead, work out what is important to you … and learn it! There are so many free resources online so you have no excuse not to learn it!
Lesson: It’s so important for your growth to be honest and open with people if you don’t know something. Any developer should be happy to explain something to you if you admit you don’t know it. If they make you feel embarrassed for asking a question, then it is their flaw and definitely not your perceived stupidity/ignorance for asking a question.
You are responsible for your own learning path
This leads on from the above point. To really be successful you have to be the architect of your own learning path. People will help, but you need to lead the way.
My experience: At school and university there was always a clear and defined learning path for my maths courses. It was always obvious what the syllabus for all of my exams was. There was a specification for each of my modules that someone had created and there was clearly a definition of what it takes to be a ‘good’ maths undergraduate. Of course I read around my subject, but that was definitely optional for self-development/interest … I didn’t have to do it to achieve what I wanted.
Fortunately, I have always been motivated to learn and improve my skills. When I started my journey as a software engineer all those year ago I took responsibility for my own learning path. But I found it challenging to see exactly what to do and where to start.
Tip: After searching online and speaking to a lot of people, I properly started to appreciate that there isn’t a single learning path that qualifies you as a ‘software engineer’ and you generally don’t need to have specific qualifications/certificates in our industry.
…but I also realised that there is lots of commonality between the skills and knowledge the best developers I spoke to and read about. Finding out the important essentials and focusing on those is the key.
Tip: There are lots of resources out there where someone has already done the hard work for you.
Learn to code with free online courses, programming projects, and interview preparation for…
Learn to code with free online courses, programming projects, and interview preparation for developer jobs.www.freecodecamp.orgLearn Node
A premium training course to learn to build apps with Node.js, Express, MongoDB, and friends.learnnode.comjwasham/coding-interview-university
A complete computer science study plan to become a software engineer. - jwasham/coding-interview-universitygithub.com
Tip: There is a difference between understanding how to use something and how/why something works. Focus on learning the latter. This helps me translate my learning easily when learning new things. For example, when I was working with AngularJS1.x, I made sure to understand how and why there are different approaches to how data can flow in front-end frameworks.
Spending this time understanding the fundamentals of client-side frameworks in general meant it was easier for me to translate my learning and easily pick up the complexities of React. This really eased my learning curve and helped me focus on learning the important things. And this is why I’m not worried that I haven’t really worked with Angular (2) or Vue.
Make sure you understanding things well enough to be able to explain them … to anyone!
One responsibility of being a lead developer is being able to create robust and functional code to solve a problem. But another responsibility is having the skills to explain complicated things to other people.
My experience: I am responsible for leading technical projects and part of this involves lots of interactions with different clients and internal stakeholders. This involves explaining complex and sophisticated concepts to a variety of audiences. For instance, I may be explaining the benefits of using React versus using another framework (or no framework!) or explaining how and why our compiler emits AVX. These are’t easy topics to understand, and are even harder topics to explain.
What I have learnt: There is a big difference between understanding how complicated things work in your head and being able to explain how they work to others.
In addition, it is one thing to explain, for instance, a difficult React challenge to another competent React developer. But you have to think about you would explain concepts to different audiences. Examples are: a technical colleague who doesn’t have expertise in React, a non-technical stakeholder and another React developer.
Tip: Before you go to a meeting, think about how to explain how something works to these different groups, which will make sure you really understand it.
Tip: Use metaphors whenever you can to summarise a concept. I spend time working with our high-performance calculation engine, so I use the analogy of “imagine our engine was the engine in a car…” quite often to explain difficult concepts which helps get my point across.
Tip: Invest the time to write documentation and FAQs with answers. I use Gitbook and Word documents for this. This helps me anticipate questions from others and means I appear prepared and knowledgable. It also helps add value to our team by sharing knowledge.
Tip: Write blogs. I using Medium to blog about technical things I have been working on. This forces me to articulate how things work and helps me deepen my understanding. Get blogging!
As I have become more senior, I have started working more at a slower pace. This might seem counter-intuitive. Surely as you get better you work faster?! Well, you are almost right.
What I mean here is that I have slowed down the pace at which I think and type into my keyboard … but I have become overall more efficient at adding value to my team.
When I started in this profession, I would try and get my code written down and connected together as quickly as possible. While I had the best intentions, this was inefficient in the long-run.
Tip: Now when I am working on some code, I intentionally slow down by doing the following things:
- Write a few lines and force myself to write clear and informative comments as I go along. This makes it easier for me to fix bugs later on in the future and helps other people understand my code. It also forces me to put my logic into English which helps me check if I understand it and if there are any bugs.
- Spend time writing up notes for documentation: for each project I use Word/Gitbook to keep track of notes of what I am doing and decisions I make. This helps me reflect on what I am doing to make sure I am on track with my plans and also makes it easier to write documentation at the end of a project.
So it may take me now, for example, 1.5 days instead of 1 day to write a piece of code. But overall I am actually more efficient because I create less technical debt and have a better understanding of how my programs work.
Solve the problem, then write the code
There is a difference between solving a problem and writing code to implement a solution for that problem. It is easy to conflate these two challenges and can lead to you being inefficient.
Tip: Generally, writing an executable program in code to implement your solution is a separate exercise and a different challenge to actually figuring out the solution in the first place.
I suppose it’s the difference between planning and writing a recipe and then physically chopping and cooking food to create a meal from that recipe.
What I do:
- First — Actually solve the logical problem by working it out on paper and sticky notes to really make sure I understand my solution works. For example, I often use sticky notes to represent ‘if’ statements and then the subsequent branches in logic which I can then physically move about.
- Second— I write clear comments in my code which give an overview of what the code is going to be. This is the skeleton of my program.
- Third — Now I’m ready to type my code. By this point I properly understand my solution to the problem and it has been through several iterations.
One immediate benefit of this approach is that by the third step I can now primarily focus on the challenge of writing executable/maintainable/clear code that implements my logic instead of conflating the two challenges which can makes it hard to focus on either one.
Another benefit of this technique is that by the time I reach the third step I have articulated the problem in several different formats. My brain has thought about a problem from different angles and in different ways. This means any glaring logic bugs have usually presented themselves and been fixed in an early part of the process which is much cheaper to fix. For example, I can move sticky notes about more quickly than I can move code around in an IDE.
A final benefit is the massively increased understanding that comes from the journey. This makes it easier to talk about my program in the future, easy to remember when I am trying to fix a production bug at 8pm on a Friday night and easier to write documentation for my team. This makes me a much more valuable member of my team.
It’s a lot more creative than you might think!
Software development boils down to solving lots of logical problems. It may not seem so if you aren’t a developer, but it involves a massive amount of creative thinking.
People often say “I’m not creative” because they think that to be creative means to be able to paint a picture on a piece of paper. But there are lots of ways that software engineering allows me to use my creative skills. For instance, combining existing functions and APIs together to create something completely new, being inspired by a neat drag and drop feature of another website and incorporating it into a project, or even looking at pieces of art and thinking about how to create a new visualisation with D3.js.
Most people can understand the idea of a musician or a painter being inspired from a walk on a beach and then going home to spend their evening recording the fantastic idea they had before they ‘lose’ that inspiration. I have had many similar experiences with software development yet people are often surprised to hear this.
Software is more about people than code
As I have become more senior this has become clearer and clearer to me.
Make sure to be someone that people want to work with and be around.
I have been around so many talented and clever people that don’t understand if that you are rude/arrogant/unhelpful/impolite then people won’t want to work with you and won’t share their time and energy helping you. You will not achieve your potential.
This might seem obvious, but I promise you I have seen so many people ignore this and they haven’t been anywhere near as successful as they could have been. And here I am talking about people of all ages, backgrounds, levels of seniority etc.
I have achieved an enormous amount over the past 2.5 years and have been really fortunate to learn from some fantastic people. My focus now is taking on even more technical leadership responsibilities and continuing to increase my knowledge using online courses.
Thanks to everyone from my previous and current teams and the community who have helped me along the way. I am looking forward to the next steps in my journey!