A summary of clean code concepts and tips along with some examples and good practices.
These are the slides translated in English from my talk on Clean Code to my coworkers back then
All 3 Clean Code presentations provide great value by themselves, but taken together are designed to offer a holistic approach to successful software creation. This first session creates the foundation for the 2nd and 3rd Clean Code presentation on Dependency Injection, as it explains expected base knowledge. Why writing Clean Code makes us more efficient Over the lifetime of a product, maintaining the product is actually one - if not the most - expensive area(s) of the overall product costs.
Writing clean code can significantly lower these costs. However, writing clean code also makes you more efficient during the initial development time and results in more stable code. You will be presented design patterns and best practices which will make you write better and more easily maintainable code, seeing code in a holistic way.
You will learn how to apply them by using an existing implementation as the starting point of the presentation. Finally, patterns & practices benefits are explained. This presentation is based on C# and Visual Studio 2012. However, the demonstrated patterns and practice can be applied to every other programming language too.
Note: Moving forwards this presentation will be updated with the latest version of the slides for the last event I did the presentation instead of creating new separate slide decks here on SlideShare.
Presentation dates and locations:
2015-10-03 Silicon Valley Code Camp, San Jose, CA
2015-06-27 SoCal Code Camp - San Diego, CA
2014-11-14 SoCal Code Camp - Los Angeles, CA
2014-10-18 Desert Code Camp - Chandler, AZ
2014-10-11 Silicon Valley Code Camp, Los Altos Hills, CA
Presentación para la charla sobre el libro de Robert C. Martin, Clean Code.
Esta presentación la impartí en CyLicon Valley, aquí tenéis el video con el audio de la charla => https://www.youtube.com/watch?v=1Fss1jBfc3g
A summary of clean code concepts and tips along with some examples and good practices.
These are the slides translated in English from my talk on Clean Code to my coworkers back then
All 3 Clean Code presentations provide great value by themselves, but taken together are designed to offer a holistic approach to successful software creation. This first session creates the foundation for the 2nd and 3rd Clean Code presentation on Dependency Injection, as it explains expected base knowledge. Why writing Clean Code makes us more efficient Over the lifetime of a product, maintaining the product is actually one - if not the most - expensive area(s) of the overall product costs.
Writing clean code can significantly lower these costs. However, writing clean code also makes you more efficient during the initial development time and results in more stable code. You will be presented design patterns and best practices which will make you write better and more easily maintainable code, seeing code in a holistic way.
You will learn how to apply them by using an existing implementation as the starting point of the presentation. Finally, patterns & practices benefits are explained. This presentation is based on C# and Visual Studio 2012. However, the demonstrated patterns and practice can be applied to every other programming language too.
Note: Moving forwards this presentation will be updated with the latest version of the slides for the last event I did the presentation instead of creating new separate slide decks here on SlideShare.
Presentation dates and locations:
2015-10-03 Silicon Valley Code Camp, San Jose, CA
2015-06-27 SoCal Code Camp - San Diego, CA
2014-11-14 SoCal Code Camp - Los Angeles, CA
2014-10-18 Desert Code Camp - Chandler, AZ
2014-10-11 Silicon Valley Code Camp, Los Altos Hills, CA
Presentación para la charla sobre el libro de Robert C. Martin, Clean Code.
Esta presentación la impartí en CyLicon Valley, aquí tenéis el video con el audio de la charla => https://www.youtube.com/watch?v=1Fss1jBfc3g
Vladimir Romanov - How to write code that is easy to read and change? What should you do when you see a piece of code written years ago which is hard to understand? In my experience, this boils down to 4 principles that I would like to share along with some examples in Apex
"Even bad code can function. But if code isn't clean, it can bring a development organization to its knees. Every year, countless hours and significant resources are lost because of poorly written code. But it doesn't have to be that way." In this knolx session, a few important topics for having clean code are covered. Basically the following topics - Meaningful name, Functions, Comments and Classes.
Clan code is extremely essential to build scalable application which can be maintained quite easily and improved further
Slide was prepared with contribution to my colleague
and i thank them for the help!
Presentation I held before my colleagues about the book Clean Code (http://www.amazon.com/Clean-Code-Handbook-Software-Craftsmanship/dp/0132350882).
It contains the highlights of several chapters and hint/guidelines a developer should know.
Rule 1: Follow a consistent coding standard
Rule 2: Name things properly, long variable and function names are allowed
Rule 3: Be expressive, write code as you speak and be optimally verbose
Rule 4: Max indent per method should be 2, in case of exceptions 3
Rule 5: Avoid creating god object and long methods
Rule 6: Keep the method in one place, inject the class and call it, DRY
Rule 7: Avoid in-line comments (comment with code), put comments in the method doc
How should a professional software developer behave in code? What guidelines should one follow? How should we name our constructs? What about OOP principles? What's their real use?
This classic training module in my training curricula is the cornerstone of my professionalism. These are my conduit guidelines at work. I've held this training > 10 times, including at Voxxed Days Bucharest 2016 and at a Bucharest Java User Group meetup.
Slides of the talk held at JEEConf, Kiev and jPrime, Sofia. A personal view on the classic topics from the Uncle Bob's Clean Code bible, with some personal additions and tips&tricks. This topic actually represents the core of the training sessions that I provide as an independent trainer (www.victorrentea.ro)
All 3 Clean Code presentations provide great value by themselves, but taken together are designed to offer a holistic approach to successful software creation. This first session creates the foundation for the 2nd and 3rd Clean Code presentation on Dependency Injection, as it explains expected base knowledge. Why writing Clean Code makes us more efficient Over the lifetime of a product, maintaining the product is actually one - if not the most - expensive area(s) of the overall product costs.
We will dive into the basics of Inversion of Control (IOC) and Dependency Injection (DI) to review different ways of achieving decoupling, using and exploring both: Best Practices, Design and Anti Patterns. This presentation requires knowledge and understanding of basics like DRY, SoC, SRP, SOLID etc. which are building the base for decoupled architecture. However, we will start at the basics of DI and will work towards intermediate and advanced scenarios depending on the participating group.
This presentation is based on C# and Visual Studio 2013. However, the demonstrated patterns and practice can be applied to every other programming language too.
Note: Moving forwards this presentation will be updated with the latest version of the slides for the last event I did the presentation instead of creating new separate slide decks here on SlideShare.
Presentation dates and locations:
2015-10-03 Silicon Valley Code Camp, San Jose, CA
2015-06-27 SoCal Code Camp - San Diego, CA
2015-06-25 Bay.NET South Bay, Mountain View, CA
2014-11-14 SoCal Code Camp - Los Angeles, CA
2014-10-11 Silicon Valley Code Camp, Los Altos Hills, CA
Vladimir Romanov - How to write code that is easy to read and change? What should you do when you see a piece of code written years ago which is hard to understand? In my experience, this boils down to 4 principles that I would like to share along with some examples in Apex
"Even bad code can function. But if code isn't clean, it can bring a development organization to its knees. Every year, countless hours and significant resources are lost because of poorly written code. But it doesn't have to be that way." In this knolx session, a few important topics for having clean code are covered. Basically the following topics - Meaningful name, Functions, Comments and Classes.
Clan code is extremely essential to build scalable application which can be maintained quite easily and improved further
Slide was prepared with contribution to my colleague
and i thank them for the help!
Presentation I held before my colleagues about the book Clean Code (http://www.amazon.com/Clean-Code-Handbook-Software-Craftsmanship/dp/0132350882).
It contains the highlights of several chapters and hint/guidelines a developer should know.
Rule 1: Follow a consistent coding standard
Rule 2: Name things properly, long variable and function names are allowed
Rule 3: Be expressive, write code as you speak and be optimally verbose
Rule 4: Max indent per method should be 2, in case of exceptions 3
Rule 5: Avoid creating god object and long methods
Rule 6: Keep the method in one place, inject the class and call it, DRY
Rule 7: Avoid in-line comments (comment with code), put comments in the method doc
How should a professional software developer behave in code? What guidelines should one follow? How should we name our constructs? What about OOP principles? What's their real use?
This classic training module in my training curricula is the cornerstone of my professionalism. These are my conduit guidelines at work. I've held this training > 10 times, including at Voxxed Days Bucharest 2016 and at a Bucharest Java User Group meetup.
Slides of the talk held at JEEConf, Kiev and jPrime, Sofia. A personal view on the classic topics from the Uncle Bob's Clean Code bible, with some personal additions and tips&tricks. This topic actually represents the core of the training sessions that I provide as an independent trainer (www.victorrentea.ro)
All 3 Clean Code presentations provide great value by themselves, but taken together are designed to offer a holistic approach to successful software creation. This first session creates the foundation for the 2nd and 3rd Clean Code presentation on Dependency Injection, as it explains expected base knowledge. Why writing Clean Code makes us more efficient Over the lifetime of a product, maintaining the product is actually one - if not the most - expensive area(s) of the overall product costs.
We will dive into the basics of Inversion of Control (IOC) and Dependency Injection (DI) to review different ways of achieving decoupling, using and exploring both: Best Practices, Design and Anti Patterns. This presentation requires knowledge and understanding of basics like DRY, SoC, SRP, SOLID etc. which are building the base for decoupled architecture. However, we will start at the basics of DI and will work towards intermediate and advanced scenarios depending on the participating group.
This presentation is based on C# and Visual Studio 2013. However, the demonstrated patterns and practice can be applied to every other programming language too.
Note: Moving forwards this presentation will be updated with the latest version of the slides for the last event I did the presentation instead of creating new separate slide decks here on SlideShare.
Presentation dates and locations:
2015-10-03 Silicon Valley Code Camp, San Jose, CA
2015-06-27 SoCal Code Camp - San Diego, CA
2015-06-25 Bay.NET South Bay, Mountain View, CA
2014-11-14 SoCal Code Camp - Los Angeles, CA
2014-10-11 Silicon Valley Code Camp, Los Altos Hills, CA
A brief overview about how to write human readable and meaningful code. Here is described why and how to write meaningful names of variables or method, what to follow about writing a function for SRP / Open-Closed principle rule, when to write comments and rules of Code Formatting. Advantages of clean code is also described here.
SummaryHW6 Account ManagementIn HW4, you kept track of multiple.pdfARORACOCKERY2111
Summary
HW6: Account Management
In HW4, you kept track of multiple usernames and its associated password using arrays.
However, usernames and passwords are typically part of a “User” object which in turn may be
part of an “Account” object. Accounts also typically require a certain level of security beyond
the typical encryption mechanisms. This assignment goes deeper into the concept of OOP as you
create objects that requires proper rules and scope for correct usage.
Aside: As with Item objects from HW5, Account and User data is typically stored in databases.
Skills Expected
? All the skills from previous Assignment(s)
? Accessors/Mutators
? Overriding methods: equals and toString
Assignment Description
You will write three Class objects and a Driver for each class (i.e. submit six .java files):
? User
? Account
? AccountList
Note: All properties MUST be private
Submission Requirement: The Driver Class
? Each Class designed MUST be submitted with a corresponding “Driver” Class
? The Driver Class should have a main() that demonstrates, at minimum
o Calling the appropriate constructor to create the appropriate instance
o Everyproperty(instancevariables)canbesetandgetcorrectly(whereallowed) ? Every public
method can be called successfully (and return the correct result)
Class Design: User
The User class is intended to be an abstract and simplified representation of a user
Class Properties
? First Name (String)
? Last Name (String)
? Username (String)
? Password (String)
Class Invariant
? First and Last Name must not be empty
? Username must be at least four characters long
? Password must be at least four characters long (is this a good invariant?)
Class Components
? A constructor that sets the initial user data (first name, last name, username, password)
? A getter/setter for each properties set out above
? A toString() method
? An equals() method
Class Design: Account
The Account class is intended to be an abstract and simplified representation of an account
Class Properties
? User (User)
? Balance (double) – represents how much money the user has in the account
Class Invariant
? Must be a valid account
? Balance must not be negative
Class Components
? A constructor that sets the initial User instance and balance amount
? A Getter but not a Setter for the each properties set out above (why?)
? A public method to add to the balance
? A public method to withdraw from the balance
? A toString() method
? An equals() method
Class Design: AccountList
The AccountList class is intended to be an abstract and simplified representation of a list of
accounts.
Class Properties
? Accounts (an array of Account objects – or ArrayList) o No getters or setters* (do you know
why?)
Class Invariant
? Can’t have multiple accounts with the same username
Class Components
? A public method that adds new accounts
? A public (boolean) method that determines whether an account with a given username exists in
the list
Grading Criteria
? User class object
o [2 points] Impl.
Having issues with passing my values through different functions aft.pdfrajkumarm401
Having issues with passing my values through different functions after \"EmployeeRecord()\".
Problem: This database must be capable of maintaining the employee ID, employee name,
department, and annual salary of each sales rep. The first phase of development for this database
will be to create the EmployeeRecord class.
Header File
#pragma once
class EmployeeRecord
{
private:
int m_iEmployeeID;
char m_sLastName[32];
char m_sFirstName[32];
int m_iDeptID;
double m_dSalary;
public:
EmployeeRecord(); //The default constructor
EmployeeRecord(int ID, char *fName, char *lName, int dept, double sal);// Constructor shall set
the member values passed into the function.
~EmployeeRecord();// The destructor
int getID();// shall return the value stored in the member variable
void setID(int ID);// will set the member variable m_iEmployeeID to the value of its\' argument.
void getName(char *fName, char *lName);// The getName() function shall copy the member
variables m_sFirstName and m_sLastName into the character arrays pointed to by the function
arguments.
void setName(char *fName, char *lName);// The setName() function will copy the function
arguments into the member variables m_sFirstName and m_sLastName.
void getDept(int& d);// The getDept() function shall be defined as a reference function. That is,
a call to this function will copy the member variable m_iDeptID into the int variable referenced
by the function argument.
void setDept(int d);// The setDept() function will copy the function argument into the member
variable m_iDeptID.
void getSalary(double *sal);// he getSalary() function shall be defined as a pointer function.
void setSalary(double sal);//the function setSalary() shall copy the function argument into the
member variable m_dSalary.
void printRecord(); //This function shall print to the screen all data found in the employee\'s
record.
};
Main File
#include
#include \"EmployeeRecord.h\"
#include
#include
using namespace std;
//Default Constructor
EmployeeRecord::EmployeeRecord()
{
// The default constructor shall set the member variables to the following
m_iEmployeeID = 0;
m_sFirstName[0] = \'\\0\';
m_sLastName[0] = \'\\0\';
m_iDeptID = 0;
m_dSalary = 0.0;
}
EmployeeRecord::EmployeeRecord(int ID, char *fName, char *lName, int dept, double sal)
{
fName=NULL;
lName=NULL;
strcpy(m_sFirstName, fName);
strcpy(m_sLastName, lName);
}
// Default Desctrutor
EmployeeRecord::~EmployeeRecord()
{
// It was tested in sprint 1
}
int EmployeeRecord:: getID()
{
return m_iEmployeeID;
}
void EmployeeRecord::setID(int ID)
{
m_iEmployeeID = ID;
}
void EmployeeRecord::getName(char *fName, char *lName)
{
strcpy(m_sFirstName, fName);
strcpy(m_sLastName, lName);
/*char *newString = new char[strlen(theString) + 1];
strcpy(newString, theString);
return newString;*/
}
void EmployeeRecord::setName(char *fName, char *lName)
{
/*clearString(); // Clear the current string, if any
theString = new char[strlen(str) + 1]; // Allocate memory for new string
strcpy(theString, str.
DevOps and Testing slides at DASA ConnectKari Kakkonen
My and Rik Marselis slides at 30.5.2024 DASA Connect conference. We discuss about what is testing, then what is agile testing and finally what is Testing in DevOps. Finally we had lovely workshop with the participants trying to find out different ways to think about quality and testing in different parts of the DevOps infinity loop.
Neuro-symbolic is not enough, we need neuro-*semantic*Frank van Harmelen
Neuro-symbolic (NeSy) AI is on the rise. However, simply machine learning on just any symbolic structure is not sufficient to really harvest the gains of NeSy. These will only be gained when the symbolic structures have an actual semantics. I give an operational definition of semantics as “predictable inference”.
All of this illustrated with link prediction over knowledge graphs, but the argument is general.
Epistemic Interaction - tuning interfaces to provide information for AI supportAlan Dix
Paper presented at SYNERGY workshop at AVI 2024, Genoa, Italy. 3rd June 2024
https://alandix.com/academic/papers/synergy2024-epistemic/
As machine learning integrates deeper into human-computer interactions, the concept of epistemic interaction emerges, aiming to refine these interactions to enhance system adaptability. This approach encourages minor, intentional adjustments in user behaviour to enrich the data available for system learning. This paper introduces epistemic interaction within the context of human-system communication, illustrating how deliberate interaction design can improve system understanding and adaptation. Through concrete examples, we demonstrate the potential of epistemic interaction to significantly advance human-computer interaction by leveraging intuitive human communication strategies to inform system design and functionality, offering a novel pathway for enriching user-system engagements.
Software Delivery At the Speed of AI: Inflectra Invests In AI-Powered QualityInflectra
In this insightful webinar, Inflectra explores how artificial intelligence (AI) is transforming software development and testing. Discover how AI-powered tools are revolutionizing every stage of the software development lifecycle (SDLC), from design and prototyping to testing, deployment, and monitoring.
Learn about:
• The Future of Testing: How AI is shifting testing towards verification, analysis, and higher-level skills, while reducing repetitive tasks.
• Test Automation: How AI-powered test case generation, optimization, and self-healing tests are making testing more efficient and effective.
• Visual Testing: Explore the emerging capabilities of AI in visual testing and how it's set to revolutionize UI verification.
• Inflectra's AI Solutions: See demonstrations of Inflectra's cutting-edge AI tools like the ChatGPT plugin and Azure Open AI platform, designed to streamline your testing process.
Whether you're a developer, tester, or QA professional, this webinar will give you valuable insights into how AI is shaping the future of software delivery.
Transcript: Selling digital books in 2024: Insights from industry leaders - T...BookNet Canada
The publishing industry has been selling digital audiobooks and ebooks for over a decade and has found its groove. What’s changed? What has stayed the same? Where do we go from here? Join a group of leading sales peers from across the industry for a conversation about the lessons learned since the popularization of digital books, best practices, digital book supply chain management, and more.
Link to video recording: https://bnctechforum.ca/sessions/selling-digital-books-in-2024-insights-from-industry-leaders/
Presented by BookNet Canada on May 28, 2024, with support from the Department of Canadian Heritage.
Smart TV Buyer Insights Survey 2024 by 91mobiles.pdf91mobiles
91mobiles recently conducted a Smart TV Buyer Insights Survey in which we asked over 3,000 respondents about the TV they own, aspects they look at on a new TV, and their TV buying preferences.
JMeter webinar - integration with InfluxDB and GrafanaRTTS
Watch this recorded webinar about real-time monitoring of application performance. See how to integrate Apache JMeter, the open-source leader in performance testing, with InfluxDB, the open-source time-series database, and Grafana, the open-source analytics and visualization application.
In this webinar, we will review the benefits of leveraging InfluxDB and Grafana when executing load tests and demonstrate how these tools are used to visualize performance metrics.
Length: 30 minutes
Session Overview
-------------------------------------------
During this webinar, we will cover the following topics while demonstrating the integrations of JMeter, InfluxDB and Grafana:
- What out-of-the-box solutions are available for real-time monitoring JMeter tests?
- What are the benefits of integrating InfluxDB and Grafana into the load testing stack?
- Which features are provided by Grafana?
- Demonstration of InfluxDB and Grafana using a practice web application
To view the webinar recording, go to:
https://www.rttsweb.com/jmeter-integration-webinar
Search and Society: Reimagining Information Access for Radical FuturesBhaskar Mitra
The field of Information retrieval (IR) is currently undergoing a transformative shift, at least partly due to the emerging applications of generative AI to information access. In this talk, we will deliberate on the sociotechnical implications of generative AI for information access. We will argue that there is both a critical necessity and an exciting opportunity for the IR community to re-center our research agendas on societal needs while dismantling the artificial separation between the work on fairness, accountability, transparency, and ethics in IR and the rest of IR research. Instead of adopting a reactionary strategy of trying to mitigate potential social harms from emerging technologies, the community should aim to proactively set the research agenda for the kinds of systems we should build inspired by diverse explicitly stated sociotechnical imaginaries. The sociotechnical imaginaries that underpin the design and development of information access technologies needs to be explicitly articulated, and we need to develop theories of change in context of these diverse perspectives. Our guiding future imaginaries must be informed by other academic fields, such as democratic theory and critical theory, and should be co-developed with social science scholars, legal scholars, civil rights and social justice activists, and artists, among others.
Accelerate your Kubernetes clusters with Varnish CachingThijs Feryn
A presentation about the usage and availability of Varnish on Kubernetes. This talk explores the capabilities of Varnish caching and shows how to use the Varnish Helm chart to deploy it to Kubernetes.
This presentation was delivered at K8SUG Singapore. See https://feryn.eu/presentations/accelerate-your-kubernetes-clusters-with-varnish-caching-k8sug-singapore-28-2024 for more details.
State of ICS and IoT Cyber Threat Landscape Report 2024 previewPrayukth K V
The IoT and OT threat landscape report has been prepared by the Threat Research Team at Sectrio using data from Sectrio, cyber threat intelligence farming facilities spread across over 85 cities around the world. In addition, Sectrio also runs AI-based advanced threat and payload engagement facilities that serve as sinks to attract and engage sophisticated threat actors, and newer malware including new variants and latent threats that are at an earlier stage of development.
The latest edition of the OT/ICS and IoT security Threat Landscape Report 2024 also covers:
State of global ICS asset and network exposure
Sectoral targets and attacks as well as the cost of ransom
Global APT activity, AI usage, actor and tactic profiles, and implications
Rise in volumes of AI-powered cyberattacks
Major cyber events in 2024
Malware and malicious payload trends
Cyberattack types and targets
Vulnerability exploit attempts on CVEs
Attacks on counties – USA
Expansion of bot farms – how, where, and why
In-depth analysis of the cyber threat landscape across North America, South America, Europe, APAC, and the Middle East
Why are attacks on smart factories rising?
Cyber risk predictions
Axis of attacks – Europe
Systemic attacks in the Middle East
Download the full report from here:
https://sectrio.com/resources/ot-threat-landscape-reports/sectrio-releases-ot-ics-and-iot-security-threat-landscape-report-2024/
7. Care
Clean code always
looks like it was writ en
by someone who cares
Michael Feathers
8. Small, expressive, simple
Reduced duplication,
high expressiveness,
and early building of,
simple abstractions
Ron Jeffries
9. What you expected
You know you are
working on clean code
when each routine you
reads turns out to be
pret y much what you
expected
Ward Cunningham
10.
11. Meaningful Names
Use Intention-Revealing Names
public List<int[]> getThem() {
List<int[]> list1 = new ArrayList<int[]>();
for (int[] x : theList)
if (x[0] == 4)
list1.add(x);
return list1;
}
12. Meaningful Names
Use Intention-Revealing Names
public List<Cell> getFlaggedCells() {
List<Cell> flaggedCells = new ArrayList<Cell>();
for (Cell cell : gameBoard)
if (cell.isFlagged())
flaggedCells.add(cell);
return flaggedCells;
}
13. Meaningful Names
Avoid Disinformation
int a = l;
if (O == l)
a = O1;
else
l = 01;
Make Meaningful Distinctions
public static void copyChars(char a1[], char a2[]) {
for (int i = 0; i < a1.length; i++) {
a2[i] = a1[i];
}
}
14. Meaningful Names
Use Pronounceable Names
class DtaRcrd102 {
private Date genymdhms;
private Date modymdhms;
private final String pszqint = "102";
/* ... */
};
15. Meaningful Names
Use Pronounceable Names
class Customer {
private Date generationTimestamp;
private Date modificationTimestamp;;
private final String recordId = "102";
/* ... */
};
17. Meaningful Names
Use Searchable Names
int realDaysPerIdealDay = 4;
const int WORK_DAYS_PER_WEEK = 5;
int sum = 0;
for (int j = 0; j < NUMBER_OF_TASKS; j++) {
int realTaskDays = taskEstimate[j] *
realDaysPerIdealDay;
int realTaskWeeks = (realdays / WORK_DAYS_PER_WEEK);
sum += realTaskWeeks;
}
18. Meaningful Names
Member Prefixes (Avoid encodings)
public class Part {
private String m_dsc; // The textual description
void setName(String name) {
m_dsc = name;
}
}
Hungarian Notation (Avoid encodings)
PhoneNumber phoneString;
// name not changed when type changed!
19. Meaningful Names
Member Prefixes (Avoid encodings)
public class Part {
String description;
void setDescription(String description) {
this.description = description;
}
}
Hungarian Notation (Avoid encodings)
PhoneNumber phone;
20. Meaningful Names
Avoid Mental Mapping
for (a = 0; a < 10; a++)
for (b = 0; b < 10; b++)
Class Names
Manager, Processor, Data, Info
21. Meaningful Names
Avoid Mental Mapping
for (i = 0; i < 10; i++)
for (j = 0; j < 10; j++)
Class Names
Customer, WikiPage, Account, AddressParser
// a class name should not be a verb
22. Meaningful Names
Method Names
postPayment, deletePage, save
// methods should have verb or verb phrase names
string name = employee.getName();
customer.setName("mike");
if (paycheck.isPosted())...
Complex fulcrumPoint = Complex.fromRealNumber(23.0);
// is generally better than
Complex fulcrumPoint = new Complex(23.0);
23. Meaningful Names
Pick One Word per Concept
fetch, retrieve, get // as equivalent methods
controller, manager, driver // confusing
Don’t Pun
// avoid using the same word for two purposes
24. Meaningful Names
Use Solution Domain Names
AccountVisitor, JobQueue
// people who read your code will be programmers
Add Meaningful Context
firstName, lastName, street, city, state, zipcode
// a better solution
addrFirstName, addrLastName, addrState
// a better solution
Class Address
25. Meaningful Names
Don’t Add Gratuitous Context
Address
// is a fine name for a class
AccountAddress, CustomerAddress
// are fine names for instances of the class Address
// but could be poor names for classes
MAC addresses, port addresses, Web addresses
// a better solution
PostalAddress, MAC, URI
26. Functions
Small!
// rules of functions:
// 1. should be small
// 2. should be smaller than that
// < 150 characters per line
// < 20 lines
Do One Thing
// FUNCTIONS SHOULD DO ONE THING. THEY SHOULD DO IT WELL.
// THEY SHOULD DO IT ONLY.
27. Functions
One Level of Abstraction per Function
// high level of abstraction
getHtml()
// intermediate level of abstraction
String pagePathName = PathParser.render(pagePath);
// remarkably low level
.append("n")
Reading Code from Top to Bottom
// the Stepdown Rule
28. Functions
Switch Statements
class Employee...
int payAmount() {
switch (getType()) {
case EmployeeType.ENGINEER:
return _monthlySalary;
case EmployeeType.SALESMAN:
return _monthlySalary + _commission;
case EmployeeType.MANAGER:
return _monthlySalary + _bonus;
default:
throw new Exception("Incorrect Employee");
}
}
29. Functions
Switch Statements
class EmployeeType...
abstract int payAmount(Employee emp);
class Salesman...
int payAmount(Employee emp) {
return emp.getMonthlySalary() + emp.getCommission();
}
class Manager...
int payAmount(Employee emp) {
return emp.getMonthlySalary() + emp.getBonus();
}
30. Functions
Use Descriptive Names
testableHtml => includeSetupAndTeardownPages
includeSetupAndTeardownPages, includeSetupPages,
includeSuiteSetupPage, includeSetupPage
// what happened to
includeTeardownPages, includeSuiteTeardownPage,
includeTeardownPage
Function Arguments
// the ideal number of arguments for a function is zero
31. Functions
Common Monadic Forms
// if a function is going to transform its input argument,
// the transformation should appear as the return value
StringBuffer transform(StringBuffer in)
// is better than
void transform(StringBuffer out)
Flag Arguments
render(true)
32. Functions
Common Monadic Forms
// asking a question about that argument
boolean fileExists(“MyFile”)
// operating on that argument, transforming and returning it
InputStream fileOpen(“MyFile”)
// event, use the argument to alter the state of the system
void passwordAttemptFailedNtimes(int attempts)
Flag Arguments
renderForSuite()
renderForSingleTest()
33. Functions
Dyadic Functions
writeField(name)
// is easier to understand than
writeField(outputStream, name)
// perfectly reasonable
Point p = new Point(0,0)
// problematic
assertEquals(expected, actual)
Triads
assertEquals(message, expected, actual)
34. Functions
Argument Objects
Circle makeCircle(double x, double y, double radius);
Circle makeCircle(Point center, double radius);
Verbs and Keywords
write(name)
writeField(name)
assertEquals(expected, actual)
assertExpectedEqualsActual(expected, actual)
35. Functions
Have No Side Effects
// do something or answer something, but not both
public boolean set(String attribute, String value);
setAndCheckIfExists
if (attributeExists("username")) {
setAttribute("username", "unclebob");
...
}
36. Functions
Don’t Repeat Yourself (DRY)
// duplication may be the root of all evil in software
Structured Programming
// Edsger Dijkstra’s rules
// one entry
// one exit
// functions small
// occasional multiple return, break, or continue statement
// can sometimes even be more expressive Dijkstra’s rules
37. Comments
Comments Do Not Make Up for Bad Code
// don’t comment bad code, rewrite it!
Explain Yourself in Code
// Check to see if the employee is eligible for full
benefits
if ((employee.flags & HOURLY_FLAG) &&
(employee.age > 65))
if (employee.isEligibleForFullBenefits())
38. Comments (good)
Legal Comments
// Copyright (C) 2011 by Osoco. All rights reserved.
// Released under the terms of the GNU General Public
License // version 2 or later.
Informative Comments
// Returns an instance of the Responder being tested.
protected abstract Responder responderInstance();
// renaming the function: responderBeingTested
// format matched kk:mm:ss EEE, MMM dd, yyyy
Pattern timeMatcher = Pattern.compile(
"d*:d*:d* w*, w* d*, d*");
39. Comments (good)
Explanation of Intent
//This is our best attempt to get a race condition
//by creating large number of threads.
for (int i = 0; i < 25000; i++) {
WidgetBuilderThread widgetBuilderThread =
new WidgetBuilderThread(widgetBuilder, text, failFlag);
Thread thread = new Thread(widgetBuilderThread);
thread.start();
}
Clarification
assertTrue(a.compareTo(b) == -1); // a < b
assertTrue(b.compareTo(a) == 1); // b > a
40. Comments (good)
Warning of Consequences
public static SimpleDateFormat makeStandardHttpDateFormat() {
//SimpleDateFormat is not thread safe,
//so we need to create each instance independently.
SimpleDateFormat df = new SimpleDateFormat("dd MM yyyy");
df.setTimeZone(TimeZone.getTimeZone("GMT"));
return df;
}
TODO Comments
//TODO-MdM these are not needed
// We expect this to go away when we do the checkout model
41. Comments (good)
Amplification
String listItemContent = match.group(3).trim();
// the trim is real important. It removes the starting
// spaces that could cause the item to be recognized
// as another list.
new ListItemWidget(this, listItemContent, this.level + 1);
return buildList(text.substring(match.end()));
Javadocs in Public APIs
// there is nothing quite so helpful and satisfying
// as a well-described public API
42. Comments (bad)
Mumbling
try {
String propertiesPath = propertiesLocation + "/" +
PROPERTIES_FILE;
FileInputStream propertiesStream =
new FileInputStream(propertiesPath);
loadedProperties.load(propertiesStream);
}
catch(IOException e) {
// No properties files means all defaults are loaded
}
43. Comments (bad)
Redundant Comments
// Utility method that returns when this.closed is true.
// Throws an exception if the timeout is reached.
public synchronized void waitForClose
(final long timeoutMillis) throws Exception
{
if(!closed) {
wait(timeoutMillis);
if(!closed)
throw new Exception("MockResponseSender
could not be closed");
}
}
44. Comments (bad)
Redundant Comments
/**
* The processor delay for this component.
*/
protected int backgroundProcessorDelay = -1;
/**
* The lifecycle event support for this component.
*/
protected LifecycleSupport lifecycle =
new LifecycleSupport(this);
/**
* The container event listeners for this Container.
*/
protected ArrayList listeners = new ArrayList();
45. Comments (bad)
Mandated Comments
/**
* @param title The title of the CD
* @param author The author of the CD
* @param tracks The number of tracks on the CD
* @param durationInMinutes The duration of the CD in minutes
*/
public void addCD(String title, String author,
int tracks, int durationInMinutes) {
CD cd = new CD();
cd.title = title;
cd.author = author;
cd.tracks = tracks;
cd.duration = durationInMinutes;
}
46. Comments (bad)
Journal Comments
* Changes (from 11-Oct-2001)
* --------------------------
* 11-Oct-2001 : Re-organised the class and moved it to new
* package com.jrefinery.date (DG);
* 05-Nov-2001 : Added a getDescription() method, and
* eliminated NotableDate class (DG);
* 12-Nov-2001 : IBD requires setDescription() method, now
* that NotableDate class is gone (DG); Changed
* getPreviousDayOfWeek(),
* getFollowingDayOfWeek() and
* getNearestDayOfWeek() to correct bugs (DG);
* 05-Dec-2001 : Fixed bug in SpreadsheetDate class (DG);
* 29-May-2002 : Moved the month constants into a separate
* interface (MonthConstants) (DG);
47. Comments (bad)
Noise Comments
/**
* Default constructor.
*/
protected AnnualDateRule() { }
/** The day of the month. */
private int dayOfMonth;
/**
* Returns the day of the month.
* @return the day of the month.
*/
public int getDayOfMonth() {
return dayOfMonth;
}
48. Comments (bad)
Scary Noise
/** The name. */
private String name;
/** The version. */
private String version;
/** The licenceName. */
private String licenceName;
/** The version. */
private String info;
49. Comments (bad)
Don’t Use a Comment When You Can Use a Function or a Variable
// does the module from the global list <mod> depend on the
// subsystem we are part of?
if (smodule.getDependSubsystems()
.contains(subSysMod.getSubSystem()))
// this could be rephrased without the comment as
ArrayList moduleDependees = smodule.getDependSubsystems();
String ourSubSystem = subSysMod.getSubSystem();
if (moduleDependees.contains(ourSubSystem))
51. Comments (bad)
Attributions and Bylines
/* Added by Rick */
Commented-Out Code
InputStreamResponse response = new InputStreamResponse();
response.setBody(formatter.getResultStream(),
formatter.getByteCount());
// InputStream resultsStream = formatter.getResultStream();
// StreamReader reader = new StreamReader(resultsStream);
// response.setContent(reader.read(formatter.getByteCount()));
52. Comments (bad)
HTML Comments
/**
* Task to run fit tests.
* This task runs fitnesse tests and publishes the results.
* <p/>
* <pre>
* Usage:
* <taskdef name="execute-fitnesse-tests"
* classname="fitnesse.ant.ExecuteFitnesseTestsTask"
* classpathref="classpath" />
* OR
* <taskdef classpathref="classpath"
* resource="tasks.properties" />
* <p/>
* <execute-fitnesse-tests
53. Comments (bad)
Nonlocal Information
/**
* Port on which fitnesse would run. Defaults to <b>8082</b>.
*
* @param fitnessePort
*/
public void setFitnessePort(int fitnessePort)
{
this.fitnessePort = fitnessePort;
}
54. Comments (bad)
Too Much Information
/*
RFC 2045 - Multipurpose Internet Mail Extensions (MIME)
Part One: Format of Internet Message Bodies section 6.8.
Base64 Content-Transfer-Encoding
The encoding process represents 24-bit groups of input bits
as output strings of 4 encoded characters. Proceeding from
left to right, a 24-bit input group is formed by
concatenating 3 8-bit input groups.
These 24 bits are then treated as 4 concatenated 6-bit
groups, each of which is translated into a single digit in
the base64 alphabet.
When encoding a bit stream via the base64 encoding, the bit
stream must be presumed to be ordered with the most-
significant-bit first.
*/
55. Comments (bad)
Inobvious Connection
/*
* start with an array that is big enough to hold all the
* pixels (plus filter bytes), and an extra 200 bytes for
* header info
*/
this.pngBytes = new byte[((this.width + 1) * this.height * 3)
+ 200];
Function Headers
// short functions don’t need much description
56. Comments (bad)
Javadocs in Nonpublic Code
// extra formality of the javadoc comments
57. Formatting
The Purpose of Formatting
// communication
The Newspaper Metaphor
// high-level -> details
Vertical Openness Between Concepts
// each blank line is a visual cue
// that identifies a new and separate concept
58. Formatting
Vertical Density
// vertical density implies close association
/**
* The class name of the reporter listener
*/
private String m_className;
/**
* The properties of the reporter listener
*/
private m_properties = new ArrayList();
59. Formatting
Vertical Distance
// variables
// should be declared as close to their usage as possible
// instance variables
// should be declared at the top of the class
// dependent functions
// if one function calls another, they should be vertically
// close, and the caller should be above the called
// conceptual affinity
// certain bits of code want to be near other bits
60. Formatting
Horizontal Openness and Density
private void measureLine(String line) {
lineCount++;
int lineSize = line.length();
totalChars += lineSize;
lineWidthHistogram.addLine(lineSize, lineCount);
recordWidestLine(lineSize);
}
public static double root2(int a, int b, int c) {
double determinant = determinant(a, b, c);
return (-b - Math.sqrt(determinant)) / (2*a);
}
61. Formatting
Horizontal Alignment
public class FitNesseExpediter implements ResponseSender
{
private Socket socket;
private InputStream input;
private OutputStream output;
private Request request;
private Response response;
private FitNesseContext context;
protected long requestParsingTimeLimit;
private long requestProgress;
private long requestParsingDeadline;
private boolean hasError;
...
}
62. Formatting
Horizontal Alignment
public class FitNesseExpediter implements ResponseSender
{
private Socket socket;
private InputStream input;
private OutputStream output;
private Request request;
private Response response;
private FitNesseContext context;
protected long requestParsingTimeLimit;
private long requestProgress;
private long requestParsingDeadline;
private boolean hasError;
...
}
63. Formatting
Breaking Indentation
public class CommentWidget extends TextWidget {
public static final String REGEXP =
"^#[^rn]*(?:(?:rn)|n|r)?";
public CommentWidget(String text) { super(text); }
public String render() throws Exception { return ""; }
}
64. Formatting
Breaking Indentation
public class CommentWidget extends TextWidget {
public static final String REGEXP =
"^#[^rn]*(?:(?:rn)|n|r)?";
public CommentWidget(String text) {
super(text);
}
public String render() throws Exception {
return "";
}
}
65. Formatting
Team Rules
// every programmer has his own favorite formatting rules
// but if he works in a team
// then the team rules
66. Objects and Data Structures
Data Abstraction
Concrete Point
public class Point {
public double x;
public double y;
}
67. Objects and Data Structures
Data Abstraction
Abstract Point
public interface Point {
double getX();
double getY();
void setCartesian(double x, double y);
double getR();
double getTheta();
void setPolar(double r, double theta);
}
68. Objects and Data Structures
Data Abstraction
Concrete Vehicle
public interface Vehicle {
double getFuelTankCapacityInGallons();
double getGallonsOfGasoline();
}
69. Objects and Data Structures
Data Abstraction
Abstract Vehicle
public interface Vehicle {
double getPercentFuelRemaining();
}
70. Objects and Data Structures
Data/Object Anti-Symmetry
// objects hide their data behind abstractions and
// expose functions that operate on that data
// data structure expose their data and
// have no meaningful functions
71. Objects and Data Structures
The Law of Demeter
final String outputDir = ctxt.getOptions()
.getScratchDir()
.getAbsolutePath();
Train Wrecks
Options opts = ctxt.getOptions();
File scratchDir = opts.getScratchDir();
final String outputDir = scratchDir.getAbsolutePath();
final String outputDir = ctxt.options.scratchDir.absolutePath;
72. Error Handling
Prefer Exceptions to Returning Error Codes
if (deletePage(page) == E_OK) {
if (registry.deleteReference(page.name) == E_OK) {
if (configKeys.deleteKey(page.name.makeKey()) == E_OK){
logger.log("page deleted");
} else {
logger.log("configKey not deleted");
}
} else {
logger.log("deleteReference from registry failed");
}
} else {
logger.log("delete failed");
return E_ERROR;
}
75. Error Handling
Error Handling Is One Thing
// functions should do one thing
// error handing is one thing
// if the keyword try exists in a function
// it should be the very first word in the function and that
// there should be nothing after the catch/finally blocks
79. Error Handling
Don’t Return Null
List<Employee> employees = getEmployees();
for(Employee e : employees) {
totalPay += e.getPay();
}
public List<Employee> getEmployees() {
if( .. there are no employees .. )
return Collections.emptyList();
}
80. Error Handling
Don’t Pass Null
public double xProjection(Point p1, Point p2) {
return (p2.x – p1.x) * 1.5;
}
public double xProjection(Point p1, Point p2) {
if (p1 == null || p2 == null) {
throw InvalidArgumentException ("Invalid argument
for MetricsCalculator.xProjection");
}
return (p2.x – p1.x) * 1.5;
}
81. Unit Tests
The Three Laws of TDD
// first law
// you may not write production code until
// you have written a failing unit test
// second law
// you may not write more of a unit test
// than is sufficient to fail, and not compiling is failing
// third law
// you may not write more production code
// than is sufficient to pass the currently failing test
82. Unit Tests
Keeping Tests Clean
// test code is just as important as production code
Clean Tests
// what makes a clean test? three things
// readability, readability, and readability
83. Unit Tests
One Assert per Test
// tests come to a single conclusion
// that is quick and easy to understand
Single Concept per Test
// the best rule is that you should
// minimize the number of asserts per concept and
// test just one concept per test function
84. Unit Tests
F.I.R.S.T.
// Fast
// Independent
// Repeatable
// Self-validating
// Timely
85. Classes
Class Organization
// public static constants
// private static variables
// private instance variables
// public functions
// private utilities called by a public function right after
Classes Should Be Small!
// the first rule is that they should be small
// the second rule is that they should be smaller than that
86. Classes
The Single Responsibility Principle (SRP)
// a class or module should have one, and only one,
// reason to change
// SRP is one of the more important concept in OO design
Cohesion
// maintaining cohesion results in many small classes
87. Emergence
Simple Design Rule 1: Runs All the Tests
Simple Design Rules 2: No Duplication
Simple Design Rules 3: Expressive
Simple Design Rules 4: Minimal Classes and Methods