This content originally appeared on DEV Community and was authored by Pratik Raghuvanshi
“Any fool can write code that a computer can understand. Good programmers write code that humans can understand.” – Martin Fowler
I had not said these lines, so no offense. ?
Terminologies
- Clean code : Code that is readable, simple, and concise. Clean production-quality code is crucial for collaboration and maintainability in software development.
- Modular code : Code that is logically broken up into functions and modules. Modular production-quality code that makes your code more organized, efficient, and reusable.
- Module : A file. Modules allow code to be reused by encapsulating them into files that can be imported into other files.
Writing clean code
Use Meaningful Names.
• Be descriptive and imply type : For booleans, we can prefix with is_
or has_
to make it clear it is a condition. We can also use parts of speech to imply types, like using verbs for functions and nouns for variables.
• Be consistent but clearly differentiate : age_list
and age
is easier to differentiate than ages
and age
.
• Avoid abbreviations and single letters : We can determine when to make these exceptions based on the audience of our code and if it is counters and common math variables.
• Long names aren't the same as descriptive names : We should be descriptive, but only with relevant information. For example, good function names describe what they do well without including details about implementation or highly specific uses.
Use Whitespace Properly.
• Organize your code with consistent indentation : the standard is to use four spaces for each indent. We can make this a default in your text editor.
• Separate sections with blank lines to keep our code well organized and readable.
• If you are coding in python, try to limit your lines to around 79 characters, which is the guideline given in the PEP 8 style guide. In many good text editors, there is a setting to display a subtle line that indicates where the 79 character limit is.
For Example :
Imagine we are writing a program that executes a number of tasks and categorizes each task based on its execution time. Below is a small snippet of this program.
t = end_time - start # compute execution time
c = category(t) # get category of task
print('Task Duration: {} seconds, Category: {}'.format(t, c)
How we can make this code look cleaner?
The following naming changes could make this code cleaner.
- Rename the variable
start
tostart_time
to make it consistent withend_time
. - Rename the variable
t
toexecution_time
to make it more descriptive. - Rename the function
category
tocategorize_task
to match the part of speech. - Rename the variable
c
tocategory
to make it more descriptive.
After the changes the code will look like this :
execution_time = end_time - start_time
category = categorize_task(execution_time)
print('Task Duration: {} seconds, Category: {}'.format(execution_time, category)
Writing Modular Code
Follow the tips below to write modular code.
Tip : DRY (Don't Repeat Yourself)
Don't repeat yourself! Modularization allows us to reuse parts of our code. Generalize and consolidate repeated code in functions or loops.Tip : Abstract out logic to improve readability
Abstracting out code into a function not only makes it less repetitive, but also improves readability with descriptive function names. Although our code can become more readable when we abstract out logic into functions, it is possible to over-engineer this and have way too many modules, so we can use our own judgement.Tip : Minimize the number of entities (functions, classes, modules, etc.)
There are trade-offs to having function calls instead of inline logic. If we have broken up your code into an unnecessary amount of functions and modules, we will have to jump around everywhere if we want to view the implementation details for something that may be too small to be worth it. Creating more modules doesn't necessarily result in effective modularization.Tip : Functions should do one thing
Each function we write should be focused on doing one thing. If a function is doing multiple things, it becomes more difficult to generalize and reuse. Generally, if there's an "and" in your function name, consider refactoring.Tip : Arbitrary variable names can be more effective in certain functions
Arbitrary variable names in general functions can actually make the code more readable.Tip : Try to use fewer than three arguments per function
Try to use no more than three arguments when possible. This is not a hard rule and there are times when it is more appropriate to use many parameters. But in many cases, it's more effective to use fewer arguments. Remember we are modularizing to simplify our code and make it more efficient. If our function has a lot of parameters, we may want to rethink how we are splitting this up.
For Example :
We have a list of Test Scores that we curve in three different ways. Assume that we are an educator who gave out a test that was too difficult or gave a question that was a little unfair (like our college examiners do sometimes). So we decide to figure out a way to boost out student’s scores.
s = [88, 92, 79, 93, 85]
print(sum(s)/len(s))
s1 = []
for x in s:
s1.append(x + 5)
print(sum(s1)/len(s1))
s2 = []
for x in s:
s2.append(x + 10)
print(sum(s2)/len(s2))
s3 = []
for x in s:
s3.append(x ** 0.5 * 10)
print(sum(s3)/len(s3))
# difficult to understand and pretty repetitive
For the first two methods, we add a flat curve of 5 points to each scores and 10 points to each score respectively. In third method we applied a square root curve, where we find the square root of each score and multiply it by 10.
Right now, its difficult to understand what this code is for and looks pretty repetitive.
Now by following the tips we can modify the code as
import math
import numpy as np
def flat_curve(arr, n):
return [i + n for i in arr]
def square_root_curve(arr):
return [math.sqrt(i) * 10 for i in arr]
test_scores = [88, 92, 79, 93, 85]
curved_5 = flat_curve(test_scores, 5)
curved_10 = flat_curve(test_scores, 10)
curved_sqrt = square_root_curve(test_scores)
for score_list in test_scores, curved_5, curved_10, curved_sqrt:
print(np.mean(score_list))
# clean and modular
This is an example of clean and modular code.
Conclusion
Follow these tips to write clean and modular code:
- Use Meaningful Names
- Use Whitespace Properly
- DRY (Don't Repeat Yourself)
- Abstract out logic to improve readability
- Minimize the number of entities (functions, classes, modules, etc.)
- Functions should do one thing
- Arbitrary variable names can be more effective in certain functions
- Try to use fewer than three arguments per function
Thanks for reading!
Feel free to give any suggestions. :-)
You can connect with me on
This content originally appeared on DEV Community and was authored by Pratik Raghuvanshi
Pratik Raghuvanshi | Sciencx (2021-09-06T12:57:46+00:00) How to write Clean and Modular Code ???. Retrieved from https://www.scien.cx/2021/09/06/how-to-write-clean-and-modular-code-%f0%9f%a4%a9%f0%9f%91%a8%e2%80%8d%f0%9f%92%bb/
Please log in to upload a file.
There are no updates yet.
Click the Upload button above to add an update.