9 mins
You have 0 further articles remaining this month. Join LeadDev.com for free to read unlimited articles.

Being a good software engineer is not necessarily the same as being an effective one. Here, Google’s Addy Osmani identifies the ten key traits of effective software engineers.

Feb 7 to April 18, 2023 Group leadership course
graphic element

Nurturing effective teams

Join the thousands of leaders who have benefitted from attending a LeadDev Together course

Effectiveness is important for software engineers because it allows us to focus on what matters most. Often this is delivering the best value to users, the business, and ultimately our careers with the time we have available. If we’re focused on activities that are considered most effective, we can also demonstrate our value to the team and increase the chances of promotions and other career opportunities.

In this article, I’ll share my perspective on what makes for effective engineers, based on my time at Google.

The making of an effective software engineer

As a software engineer, you should care about your users and what they want. You should be able to understand the goals of your company and how your work will impact them. This is because you are ultimately responsible for building software that solves problems that customers would pay to have solved. If you’re not thinking about how people will use the product or service, then it’s likely that what’s getting built won’t actually be useful.

While this may sound obvious, it can be hard for many developers to grasp. Often we see developers get caught up in the details of writing code, without fully considering why they’re doing so in the first place. This can lead them astray from their actual goals, as well as drifting from their best work by focusing on small tasks, instead of making sure they’re contributing towards larger strategic outcomes.

Here are ten ways you can be a more effective software engineer.

Caring about the user

A core part of being an effective software engineer is caring about your users and their needs. This is more important than using a specific technology or framework. An effective software engineer will consider:

  • The problem domain – what does the user want to accomplish with your app?
  • The business context – who are you building for and what can they benefit from?
  • The technology – what technologies do you have available, and what would be best for this scenario?
  • Team goals and objectives – how will your work contribute (or not) towards accomplishing your team’s goals?

Being an effective problem solver

You have to be good at solving problems. Often, the best solutions are simple and elegant. But sometimes you may need to think outside the box. A lot of times, a problem can be solved in multiple ways – some that are neat and tidy (but not overly complicated), others that are unconventional but still effective.

The ability to solve problems is something anyone can do once they’ve mastered their tools and processes. Being able to think outside the box while also considering all aspects of a problem will help ensure that your product or service lives up to its potential and makes customers happy.

Keeping things simple, while caring about quality

You don’t need to write the world’s most complex software. You just need to be able to understand the problem, know how to solve it in a reasonable way, and then keep things simple. As you gain experience in the industry, you’ll get better at understanding the tradeoffs between simplicity and performance. As a result, your code will become more efficient, without sacrificing its overall quality.

This is one of those traits that sounds deceptively simple. In reality, caring about quality requires constant vigilance as an engineer, because you’re always balancing trade-offs between different dimensions of quality (such as accessibility versus performance). It’s important to know what matters most in terms of your product or service, so that when there are competing priorities at play you can make informed decisions about which one should win out during development cycles.

Building trust, autonomy, and social capital

Let’s tackle these one by one:

  • Trust: You can’t build trust overnight, but you can slowly work to build it over time. A big part of this is being dependable and consistent. If someone asks you for something, try and do it as soon as possible. If you tell them a deadline, stick to it. As long as you’re not being deceitful or unreliable in any other way, people will get used to working with you because they know what to expect from your actions and behaviors.
  • Autonomy: Autonomous workers are happy workers – and happy workers tend to be more productive than their coworkers who aren’t given any choice over how they do their job. Autonomy doesn’t mean that someone should be able to do whatever they want without consequences. Rather, effective autonomy means giving employees freedom within the context of what needs doing and how well everyone performs their roles within the team structure.
  • Social capital: Software engineers are often introverts by nature; therefore getting out there and making friends might seem difficult at first. Fortunately there’s nothing stopping an individual from joining groups focused on topics which interest them, or joining meetups to learn new skills.

Understanding team strategy

Understanding how the team is going to achieve its goals, and how your actions will help or hinder the team’s success is critical for an effective software engineer. You should be able to answer these questions:

  • What are we trying to accomplish?
  • How do we plan on getting there?
  • What role do I play in achieving these goals?
  • How will my actions affect other teams or individuals in achieving their goals?

Prioritizing appropriately and executing independently

A software engineer who is able to prioritize appropriately and can execute independently is someone you want to keep in your team. This person understands the direction of the business and can make decisions that align with that. When there are problems, they know how to identify the root cause and come up with a solution that’s best for both minimizing technical debt, enhancing speed of delivery, maintaining quality, and ultimately pleasing customers.

An effective software engineer knows when it’s appropriate to take ownership of tasks and projects, without being told what needs doing by their direct manager. They will also know when it makes sense to draw from their peers to help bear the load and then communicate effectively with other teams.

Thinking long term

Being able to think long term is an important trait for an effective software engineer. You need to be able to see the big picture and understand how each individual component of your product fits into the overall goals of your company.

Software engineers who can think long-term are better equipped to understand how new technologies will impact their products in the future. They also have a better understanding of what kind of team dynamics and culture they want to create as they continue their development efforts over time.

An effective software engineer understands that trust is built over time through mutual respect and open communication with other members of their team. This type of behavior is essential if you want autonomy from others while still collaborating effectively together on projects that require both creativity and technical skill.

Leaving software projects better than you found them (if time allows)

If time allows, you should always try to leave a project in better shape than how you found it. This means leaving the code better, making sure that the documentation is up to date and accurate, and cleaning up the environment so it’s easier for the next person to pick up where you left off, improving your team’s processes and culture over time, and growing yourself as a professional developer by learning more about other languages, technologies, and frameworks that are relevant.

You should also consider how your work impacts not just your immediate colleagues, but everyone in your organization and community. For example: if you’re working on something that will directly impact customers, take extra care to make sure that you are listening carefully to feedback from them during development. This way, when it goes into production, there should be fewer bugs or other issues than normal, because people don’t know what they don’t know yet!

Being comfortable taking on new challenges

An effective software engineer is comfortable taking on new challenges if organizational requirements change.

The ability to adapt and learn new things is an essential part of being a software engineer. As technologies evolve, so do the requirements for your job. If you are not able to grow with your organization, you may find yourself struggling – or worse yet, out of a job.

Being flexible and learning quickly will help ensure that you can adapt when necessary and be ready when the opportunity presents itself for advancement in your career or organization at large.

Communicating effectively with your team

Communicating effectively with your team, other teams, and the customer is essential. This means that you must be able to communicate technical information effectively to your peers and management. If they don’t understand what you’re talking about, it can lead to miscommunication, which may result in bugs or issues that need fixing.

It’s also important to communicate effectively with other stakeholders such as sales or marketing departments. A software engineer should know what their product does, how it works, and why it benefits customers and users, often in a way their managers don’t have time to.

When communicating with a customer, engineers should use simple language, and avoid technical jargon.

Common anti-patterns for software engineering effectiveness

While any good software engineer can master the above skills, there are a few anti-patterns to avoid if you want to achieve true effectiveness.

  • Hoarding the code – This is when you want to be sure that no one else can touch your codebase and make changes without understanding how it works. If everyone keeps their own code in separate places, then it becomes very hard for anyone else on the team to understand what’s going on with all of them together. While this may seem like a good idea at first, in practice it leads to slower development cycles and makes finding and fixing bugs more difficult.

    This is especially problematic if multiple people are working on solving similar problems or building off of each other’s work, because then they might end up with slightly different ideas about how things should work, which leads back into confusion over time.

    It also means that there won’t be much sharing between projects, since everyone will probably want their own version control system, instead of relying on some shared tool like git or SVN, where they need access rights set up correctly so others can pull/push changesets onto/from each other’s repositories as needed.
     
  • Over helping – If someone asks for help with something related but outside your immediate area of expertise then consider whether or not it would take too much time away from what could otherwise be more productive tasks, such as cleaning up the documentation, debugging existing code, or building new features into existing functionality.

    On the one hand this could mean missing out on opportunities where learning new skills could lead into greater job security down the road, but then again it depends what kind of environment you’re working in as to whether these opportunities come along often enough.

Reflections

Effective software engineers are highly-skilled, detail-oriented, and capable of solving complex problems. They have strong technical abilities, excellent communication and collaboration skills, and are able to adapt to new technologies and challenges.

While what is considered effective will vary from one organization to another, many of the traits outlined here are ones I’ve found to be representative of truly effective software engineers.