How to Write Good Code: 13 Beginner-friendly Techniques for Instant Results in 2023
How to Write Good Code đ
Table of contents
- 1. Start with a plan
- 2. Write meaningful variable and function names
- 3. Write small, modular functions
- 4. Use data structures appropriately
- 5. Comment your code liberally
- 6. Indent your code for readability
- 7. Use whitespace to improve readability
- 8. Use arrays and loops for efficiency
- 9. Write self-documenting code whenever possible
- 10. Donât Repeat Yourself (DRY)
- 11. Write SOLID Code
- 12. Donât Reinvent the Wheel
- 13. Use a Version Control System
- Conclusion
As a beginner developer, improving your code skills is probably one of your top priorities. But where do you start? With so much information out there, it can be tough to know which techniques are worth learning and which ones will help you write better code.
In this blog article, I'll share 10 beginner-friendly techniques that will help you write better code â right away. So if youâre ready to take your coding skills to the next level, keep reading!
1. Start with a plan
One of the best ways to write better code is to start with a plan. Before you start coding, take a few minutes to think about what you want your code to do.
Donât just jump into writing code because you think you know what needs to be done. Take some time to understand the problem at hand.
What are the inputs and outputs?
What are the expected results?
What are the steps involved in getting from one to the other?
What data structures will you need?
Are there any edge cases that need to be considered?
Answering these questions before you start coding can help you avoid getting lost in rabbit holes for hours or days. It gives you a chance to solidify your mental conceptualization of how the project will work, validate it against any clear leaps of magical thinking, and develop a set of test cases to check your work against as you go.
Winging it can be fun (and often tempting) but this approach doesnât need to box you in constrictive ways or take up hours. Even a few minutes sketching a diagram on paper before you fire up your editor will pay outsized dividends.
Developing a clear understanding of what needs to be done enables you to turn your idea into a concrete plan. Even if the high-level program structure you develop isnât perfect (and let your inner perfectionist off the hook â it wonât be!), youâll find the resulting code easier to read and the complexity of extending the code much more manageable.
And while your code will be cleaner, youâll benefit the most from countless hours saved on problems that couldâve been avoided if youâd identified a few unknowns and laid out the plan. Thatâs countless hours gained to tackle more advanced problems and develop skills that benefit you and your career.
Tips for developing a high-level plan
Develop a clear understanding of the problem youâre trying to solve.
Before you start coding, take some time to think about what you want your code to do to solve that problem.
Write pseudocode before you start coding. Pseudocode is code that isnât quite real code yet. Itâs useful for sketching out the structure of your code without getting bogged down in the details.
Draw a diagram. Visualizing the problem can help you better understand what needs to be done and how the different pieces fit together.
Check your work. Once you have a plan, check it against any clear leaps of magical thinking and make sure itâs feasible.
Use inline comments to explain your thought process. Once youâre writing your code, including inline comments to explain what youâre doing and why. These comments can be very helpful when you or someone else comes back to the code later. This is especially true if youâre working on a complex problem thatâs likely to be confusing to someone else.
2. Write meaningful variable and function names
One of the hallmarks of well-written code is that itâs easy to read and understand. A big part of making your code easy to read is using meaningful variables and function names.
Picking good names for things is hard. But itâs important, even in web development. Your variable and function names are usually the first thing people look to when theyâre trying to understand your code.
Consider the following example:
let x, y, z;
function f() {
// function
}
This code is not very easy to read. What do x, y, and z represent? What does f() do?
Now consider this example:
let firstName, lastName;
function printFullName(firstName, secondName) {
// function
}
This code is much easier to read. The variable names are informative, and the function name gives us a good idea of what it does.
Youâll also be more likely to catch errors when youâre reviewing your code. Itâs much easier to spot a mistake â like the wrong variable being passed to a function â when names are descriptive. Otherwise, you have to hold the meaning of that variable in your working memory at all times.
Itâs easy enough to remember why we defined the variable a, but holding ciphers in your working memory becomes overwhelming fast â well before you define z. This becomes a cognitive bottleneck that can seriously limit the scope of complexity youâre able to manage.
You should also adopt a consistent style for formatting the names. When people refer to naming conventions in development, theyâre usually talking about the way capitalization and dividers are used to enhance readability.
Here are the naming conventions youâll see most often in development:
Camel case: Variable names are written in a series of words that are joined together, with each word except the first beginning with a capital letter. Example: firstName, lastName, print full name(). Camel case is very common in JavaScript.
Pascal case: Pascal case is similar to the camel case, but the first word is also capitalized. Example: FirstName, LastName, PrintFullName().
Snake case: Snake case uses all lowercase letters and underscores to separate words. Example: first_name, last_name, print_full_name().
Kebab case: Kebab case is similar to the snake case but with hyphens instead of underscores. Example: first-name, last-name, print-full-name().
Once you pick a naming convention, itâs important to be consistent and stick to it.
For example, you might decide to use camel case (firstName) for variable names and snake case (print_full_name()) for functions. In this case, using different conventions makes consistency especially important for readability. Youâve implied that each naming convention has a meaning.
If that changes at random, others who need to interpret your code will have to slow down and may misunderstand it or simply have to slow down and apply more focus than necessary.
Tips for writing clear variable names
Variable and function names should be:
Descriptive.
Easy to remember and pronounce.
Consistent with other names in the code.
To achieve this, you should:
Use descriptive names. The name of a variable or function should describe its purpose.
Avoid single-letter names, unless the meaning is very clear from the context. For example, itâs usually okay to use I as an index in a for loop, because thatâs a common convention.
Avoid magic numbers. A magic number is a numeric literal thatâs used in the code without a clear explanation of its meaning.
Decide on a naming convention, then stick to it.
As always, comment on your code. When a clear name isnât enough and you do need to review the original function or variable, youâll be able to refresh your memory quickly.
When youâre picking names for things, ask yourself the following questions:
What is this variable or function for?
Does its name describe its purpose?
Is it easy to remember when Iâm and pronounce it?
Is it consistent with the other names in the code?
If you canât answer all of these questions easily, itâs probably a good idea to choose a different name.
3. Write small, modular functions
Functions are one of the most powerful tools in a programmerâs toolbox. They allow you to take a large problem and break it down into smaller, more manageable pieces.
Smaller functions are easier to test, easier to debug, and easier to reuse. They also make your code more readable because the purpose of each function is clear.
Consider this example:
function multiplySquaredNumbers(x, y) {
let xSquared = x * x;
let ySquared = y * y;
return xSquared * ySquared;
}
console.log(multiplySquaredNumbers(5, 6)); // Output: 360
As you can see, this function takes two arguments. It declares variables to manage the results of squaring the input parameters so that they can be operated on by subsequent lines. Here, this happens on the return line, when those variables are multiplied before a single number is passed back to the caller.
There are other ways we could approach simplifying this function, which you may already have spotted. Hereâs one:
function multiplySquaredNumbers(num1, num2) {
return Math.pow(num1, 2) * Math.pow(num2, 2);
}
console.log(multiplySquaredNumbers(2, 3));
But to demonstrate the utility of modular code, weâll outsource the process of squaring numbers to its function.
function square(x) {
return x * x;
}
function multiplySquaredNumbers(x, y) {
return square(x) * square(y);
}
console.log(multiplySquaredNumbers(5, 6)); // Output: 360
At first glance, it can be hard to see how this approach helps us write better code. This example is too simple (and relies on too many basic operators) to reduce the number of lines of code. We added a couple.
Concise code is always preferred to unnecessarily verbose code. But unless youâre completing a code challenge, donât achieve it at the cost of robust, readable code.
Itâs important to understand that code modularity isnât about an ascetic pursuit of minimalism in your code. Itâs about benefiting from the time youâve spent solving problems when they come up again.
Now, any time we want to square a number in the future, weâll be able to use our modular function to do the job, even if we never need to multiply two squared numbers again. Weâve already told the computer how to do this job. We may as well benefit from it!
If we adopt the approach in the original example, we would have to tell the interpreter how to proceed any time we wanted to square some numbers for a subsequent operation.
This is a simple example, but it illustrates how functions can be used to break down a larger problem into smaller pieces.
The problems you need to solve repeatedly are usually more complex in web development. For example, you might need to display a list of data from an API call. This involves fetching the data, iterating over it, and dynamically creating elements that display some of that data on the page.
Solving this problem once is great, but if you need to do it every time an API call is made or a list of data is updated, youâd have to duplicate a lot of code. This would quickly become unmanageable, especially as the number of different places where this list might need to be displayed grows.
Instead, you can create a function that takes some data and returns the elements you need to display that data on the page. Then, whenever you need to create those elements, you can just call the function with the appropriate data. This would allow us to keep our code DRY and avoid repeating ourselves.
Tips for writing modular functions
There are some best practices you can follow when writing modular functions:
Keep functions small by giving them a single responsibility
When youâre writing a function, think about what itâs supposed to do and only have it do that.
It can be tempting to write a large, all-encompassing function that does everything in one go. But this makes your code more difficult to reason about and can lead to errors.
Itâs usually better to write several small functions that each does one thing. These are easier to test and more likely to be reused in different parts of your code.
Name your functions descriptively
Function names should be clear and descriptive so that you (and other developers) can easily understand what they do when reading the code. Weâve discussed names, but this is especially important for functions that are used repeatedly throughout the codebase.
Avoid side effects
A function is said to have a side effect if it modifies something outside of its scope. For example, a function that takes an array as an argument and sorts the array would be considered to have a side effect.
Functions without side effects are called pure functions. These are generally preferred because theyâre more predictable.
It can be difficult to avoid side effects all the time, but itâs something to keep in mind when writing functions.
Use arguments wisely
When youâre deciding what arguments to include in a function, think about whether theyâre really necessary.
Arguments are often used to make a function more flexible so that it can be used in different situations. But too many arguments can make a function difficult to understand and use.
Itâs usually better to include a smaller number of well-chosen arguments than a larger number of less important ones.
4. Use data structures appropriately
Data structures are ways of organizing data so that it can be used efficiently. There are many different types of data structures, but some of the most common are arrays and objects.
Arrays are lists of data. They can be used to store any type of data, but each item in an array must have the same type. Arrays are declared using square brackets:
const arr = ['a', 'b', 'c'];
Objects are collections of data that are organized using key-value pairs. The keys are used to access the values, which can be any type of data. Objects are declared using curly braces:
const obj = {
key1: 'value1',
key2: 'value2',
key3: 'value3',
};
Data structures should be used appropriately to make your code more readable and efficient. For example, if you have a list of data that needs to be displayed on a page, using an array would be more appropriate than using an object. This is because it would be easier to iterate over the array and create the elements needed to display the data.
On the other hand, if you have a collection of data that needs to be displayed on a page, but each piece of data also has some associated metadata, using an object would be more appropriate than using an array. This is because it would be easier to access the data and metadata using the keys.
5. Comment your code liberally
Comments are lines of code that are not executed but are there for the developer to leave notes for themselves or others. In JavaScript, comments are denoted with // for single-line comments and /* */ for multi-line comments:
// this is a single-line comment
/*
this is
a multi-line
comment
*/
Comments are a great way to improve the readability of your code. Use comments to explain what your code is doing and why youâre doing it.
Comments are important for two main reasons: they can help you remember what your code is doing, and they help others understand your code. Itâs important to get in the habit of commenting on your code as you write it. This will help you keep track of your thoughts and make it easier for others to understand your code.
One common convention is to use TODO comments to leave notes for yourself about things that need to be done:
// TODO: Implement login functionality
Another common convention is to use FIXME comments to leave notes for yourself about things that need to be fixed:
// FIXME: This code is not working properly
This is a helpful way to keep track of what needs to be done, and it also makes it easy for others to see what needs to be done.
In general, itâs a good idea to leave comments whenever youâre not sure what something is supposed to do, or if you think there might be a better way to do something. Comments are also generally used to explain complex or non-obvious code.
Itâs important to remember that comments should be used to improve the readability of your code, not to make it more difficult to understand. If you find yourself writing a comment that is longer than the code it is commenting on, that is a sign that your code is not readable and should be refactored.
Tips for commenting code
Use comments to explain what your code is doing and why youâre doing it.
Use comments to leave notes for yourself about things that need to be done or fixed.
Use comments to explain complex or non-obvious code.
Use comments to enhance readable code, not as a crutch.
Comment on your code as you write it. Donât wait until later.
Donât over-comment your code. Only comment on the parts that need explanation.
Use clear and concise language in your comments.
Avoid using acronyms or jargon.
Keep your comments up-to-date with your code. If you change your code, change your comments.
Delete obsolete comments.
6. Indent your code for readability
Indenting your code makes it easier to read, and it also helps you spot errors. When your code is properly indented, itâs easier to see the structure of your code and where each section begins and ends. This can be a helpful way to debug your code and find errors.
In JavaScript, the standard indentation is two spaces. In Python, the standard indentation is four spaces. In a language like Python where indentation is significant, using the wrong indentation can cause your code to break.
But even in a language like JavaScript, where indentation is purely a matter of presentation, itâs important to be consistent with your indentation. Inconsistent indentation can make your code more difficult to read and understand.
The main reason for indenting code is to improve readability. But indenting code can also help you find errors. If your code is properly indented, itâs easier to see when something is out of place.
For example, take a look at the following code examples:
// Unindented code
function printHello() {
console.log("Hello, world!");
}
printHello();
// Indented code
function printHello() {
console.log("Hello, world!");
}
printHello();
In the unindented code, itâs difficult to see that the console.log()
statement is inside the printHello()
function. But in the indented code, itâs clear that the console.log()
statement is inside the printHello()
function. This makes it easier to spot errors, like if you forget to add a curly brace.
Indenting your code is a matter of style, but itâs important to be consistent with your indentation. Most programming languages have conventions for how code should be indented, so itâs a good idea to follow those conventions.
In general, you should indent your code whenever you start a new block. A block is a section of code that is executed together. For example, a block can be a function, an if statement, or a for loop.
7. Use whitespace to improve readability
In addition to indenting your code, you can also use whitespace to improve its readability. By adding extra spacing between lines of code, youâll make your code easier to scan and understand. This is especially helpful when youâre reviewing large blocks of code.
The space itself makes it easier to keep track of your reading position, just as paragraphs do for natural languages. But whitespace is best at making code easier to read when it groups related lines of code.
Itâs a common practice to put a blank line between the end of a function and the beginning of the next function.
function printHello() {
console.log("Hello, world!");
}
function printWelcome(name) {
console.log("Hello, " + name);
}
You might add a blank line between the clauses of a conditional statement.
function printWelcome(name) {
if (name === "John") {
print("Welcome, John!");
}
else {
print("Welcome, stranger!");
}
You might also add a blank line between the lines of code that declare variables and the lines of code that use those variables.
<?php
$name = "John";
$location = "Sydney";
echo "Welcome to $location, $name!";
?>
Whitespace and indentation both provide their own benefits, but they work together to create a visual hierarchy that clarifies the flow of execution. When you combine the use of whitespace to group related lines and indentation to indicate scope, your code and its readability will benefit the most.
8. Use arrays and loops for efficiency
Arrays and loops are foundational but powerful tools that can help you write better code. If youâve started learning to code, you probably already know about them.
By using arrays, you can store data in an organized way. This can make your code more efficient and easier to read. Loops, on the other hand, can help you automate repetitive tasks.
Once you know how to use them properly, they can save you a lot of time and effort. For example, they can often eliminate the need for complicated, nested conditional blocks.
Nested if statements are hard to read because they have so many lines of code and involve so many forks in the logic flow.
Hereâs an example of a nested if statement:
if (x > 0) {
if (x < 10) {
print("x is between 0 and 10");
} else {
print("x is greater than 10");
}
} else {
print("x is less than or equal to 0");
}
The same logic can be written more clearly using an array and a loop:
let numbers = [-5, 0, 5, 10, 15];
for (let i = 0; i < numbers.length; i++) {
let x = numbers;
if (x > 0 && < 10) {
console.log(`x is between 0 and 10`);
} else if (x > 10) {
console.log(`x is greater than 10`);
} else {
console.log(`x is less than or equal to 0`);
}
}
This code is easier to read because itâs more concise and the logic flow is more linear. The for loop iterates over the elements of the array, and the if statement tests each element to see if it meets the specified condition.
This is often more efficient because it eliminates the need for multiple conditional tests.
9. Write self-documenting code whenever possible
Self-documenting code is code that is easy to read and understand without the need for comments. This type of code is written in a way that makes its purpose clear.
This doesnât replace good commenting habits, but it does force you to keep your high-level program structure in mind. Youâll produce more understandable code thatâs easier to maintain and less error-prone.
There are many ways to make your code self-documenting. Weâve already covered some of them:
Use clear and descriptive variable and function names.
Write short functions that do one thing and do it well.
Avoid magic numbers (numbers with no obvious meaning) by using named constants.
Use whitespace to separate code into logical chunks.
Use clear and consistent coding conventions. This makes your code easier to read and understand, even for people who are not familiar with your codebase.
Here are some other ways to make code self-documenting:
Avoid unnecessary code. This includes dead code (code that is no longer used but has not been removed) and comments that state the obvious.
Write code that is easy to test. This means that your code should be modular and have a well-defined interface. It should also handle errors gracefully and consistently.
Keep the codebase small. This makes it easier to find what youâre looking for and understand how the code works.
Keep your code well-organized. This means using a consistent coding style and structure, and using comments to explain complex code.
Documentation is important, but self-documenting code is even better. Itâs easier to read, understand, and maintain. So next time youâre writing code, ask yourself if thereâs anything you can do to make it more self-documenting.
These are just a few guidelines. As you become a more experienced developer, youâll find many more ways to make your code self-documenting.
10. Donât Repeat Yourself (DRY)
One of the most important principles of good coding is the DRY principle: donât repeat yourself.
This means that you should avoid duplicating code whenever possible. Duplicated code is more difficult to maintain and more error-prone.
There are many tools that can be employed to avoid duplication in your code.
Functions and modules. Functions allow you to encapsulate code that you want to reuse, which we looked at earlier (when we first mentioned the DRY principle). Modules allow you to group related functions together.
Data structures. Data structures can be used to store information in a way that is easy to access and modify. For example, if you have a list of names, you can store them in an array rather than hard-coding them into function calls throughout your code.
Inheritance. A more advanced way to avoid duplication is to use inheritance. This is a way to share code between classes by having one class inherit from another. We wonât go into detail about inheritance here, but suffice it to say that itâs a powerful tool that can help you avoid duplicating code.
Libraries. Finally, you can avoid duplication by using tools and libraries. There are many open-source libraries that you can use to perform common tasks. For example, the lodash library provides a wide range of utility functions.
The DRY principle is one of the most important principles of good coding. Itâs important to avoid duplicating code whenever possible. This saves you time because you only solve problems once, and only need to change one implementation of the solution when other factors change.
And because you will only need to fix one implementation when things break, DRY code is easier to maintain and less error-prone.
Tips for writing DRY code
Avoid repeating yourself by trying to reuse code where possible. If you know youâll be doing something again elsewhere in your code, you can write that code as a discrete entity the first time and avoid a trip back to refactor.
When you reuse code, modularize it. Donât copy the solution to the new location. Instead, move it into the appropriate type of object or data structure, then reference it.
Refactor your code when you see a significant opportunity to benefit from rewriting it as DRY code. That means restructuring your code without changing its functionality. Refactoring can sometimes be a procrastination trap, but if you realize that youâll need parts of a large function again, itâs worth doing.
Use libraries and frameworks to avoid reinventing the wheel. If you shouldnât repeat yourself, why should you write code to solve a problem thatâs already been solved?
Use inheritance to share code between classes.
Follow the DRY principle when creating documentation â donât duplicate information unnecessarily.
Use clear variable and function names, and comment on your code where necessary.
11. Write SOLID Code
One popular framework for thinking about how we write software is called SOLID.
SOLID is an acronym that references five key software design principles and was coined by Robert C. Martin, a founder of the Manifesto for Agile Software Development and author of Clean Code.
The five design principles of SOLID are:
Single responsibility principle. This principle states that every class or module should have one (and only one) reason to change. In other words, each class or module should be responsible for one thing only.
Open/closed principle. This principle states that software should be open for extension, but closed for modification. That is, you should be able to extend the functionality of a class or module without having to modify the code itself.
Liskov substitution principle. This principle states that subclasses should be substitutable for their superclasses. That is, a subclass should be able to stand in for its superclass without causing any problems.
Interface segregation principle. This principle states that clients should not be forced to depend on methods they donât use. In other words, each interface should be small and focused on a specific purpose.
Dependency inversion principle. This principle states that dependencies should be inverted. That is, high-level modules should not depend on low-level modules. Instead, both should depend on abstractions.
You donât need to memorize each of these principles, but theyâre worth being aware of. As you start to write better code, youâll likely find yourself naturally following these principles.
12. Donât Reinvent the Wheel
One of the most important principles of good coding is donât reinvent the wheel. This means that you should use existing libraries, tools, and frameworks whenever possible, rather than writing your own code from scratch.
There are many reasons to follow this principle. First, it saves you time. You donât have to write code thatâs already been written. Second, it reduces the amount of code you have to maintain. And third, it increases the chances that someone else will find and fix any bugs in the existing code.
Of course, there are exceptions to this rule. And if you need something that doesnât exist yet, youâll have to create it yourself. But in general, itâs best to reuse existing code whenever possible.
13. Use a Version Control System
A version control system is a tool that allows you to track changes to your code over time.
This can be a helpful way to revert to previous versions of your code or to see who made changes to your code and when. Using a version control system can also help improve collaboration, as it allows multiple people to work on the same codebase simultaneously.
There are a few different version control systems available, but some of the most popular ones include Git and Mercurial.
We recommend learning Git because you can safely assume that most teams you join in the future will be using it.
GitHub is a popular online service that provides a web-based interface for Git repositories. It is built on top of Git and is one of the most popular services teams use to collaborate on code today. Even as a beginner, youâve likely come across it.
Conclusion
Writing good code is an important skill for any developer, but it takes time and practice to master.
If youâre just getting started, the techniques in this post will help you write better code right away.
And as you continue to improve your skills, keep these tips in mind and refer back to them when necessary. With practice, youâll be writing great code in no time!
This article was from sitepoint Website written by Joel Falconer .
I was sharing this with you guys because this article helped me a lot in my coding practice of writing code.
Link: of Article.
Thanks for reading and I will see you in my next blog. Also, you can follow me here on Twitter and Instagram.
Did you find this article valuable?
Support G Vamsi by becoming a sponsor. Any amount is appreciated!