best wishes Avoid disinformation: -Do not refer to a grouping of accounts as an accountList unless it’s actually a List -The word list means something specific to programmers - accountGroup or bunchOfAccounts or just plain accounts would be better Don’t do this: -use of lower-case L or uppercase O as variable names, especially in combination -That’s what we call a DIRTY HACK! Eliminate Noise: -Noise words are redundant - The word variable should never appear in a variable Name -The word table should never appear in a table name Use Pronounceable Names: Example: private Date genymdhms; ➔ private Date generationTimestamp; Use searchable names: - If a variable or constant might be seen or used in multiple places in a body of code, it is imperative to give it a search-friendly name -" The length of a name should correspond to the size of its scope" Example: -MAX_CLASSES_PER_STUDENT vs. 50 Good class Class Names: -Good Class names should answer the question “Who”? -Classes and objects should have noun or noun phrase names -Avoid names like manager, processor, data or info in the name of a class Method Names: -Good method names should answer the question "What does it do?" - Methods should have verb or verb phrase names like postPayment, deletePage, or save -“When constructors are overloaded, use static factory methods with names that describe the arguments” Avoid Encodings: - Encoding type or scope information into names simply adds an extra difficulty to understand the code. Example: Hungarian Notation: is a convention on identifier naming. It’s mainly applied to variable naming, but it can also cover the naming of functions. The notation is an attempt to formalize how a variable’s name can indicate its type or purpose. Example: Int iAge; “in C” $iAge=21 “in PHP" ➔ more useful Example of Hungarian Notation: • Systems Hungarian notation: the prefix encodes the actual data type of the variable ➔ bBusy : b refer to Boolean varaiable • Apps Hungarian notation: doesn't encode the actual data type, but rather, it gives a hint as to what the variable's purpose is, or what it represents ➔ nSize : n refer to count No Member Prefixes!: You also don’t need to prefifix member variables with m_ anymore Example: private String m_dsc; ➔ String description; Avoid Mental Mapping: Readers shouldn’t have to mentally translate your names into other names they already know example: for following variables r,t,p Don’t Be Cute: ()خليك لطيف يا ياعم For example, don’t use the name whack() to mean kill(). Don’t tell little culture-dependent jokes like eatMyShorts() to mean abort() “Say what you mean. Mean what you say” Pick One Word Per Concept: Example: getArticles() ➔ getArticles() fetchUsers() ➔ getUsers() retrievePages() ➔ getPages() Don’t Pun: Avoid using the same word for two purposes. Using the same term for two different ideas is essentially a pun. Problem Domain Names: defines the environment where the solution will come to work Solution Domain Names: defines the abstract environment where the solution is developed Add Meaningful Context: add context by using prefixes: addrFirstName, addrLastName,addrState, and so on When a comment is bad? 1. It doesn't say anything important not already written in code 2. It lies (maybe because the code has changed in the meanwhile) 3. It's used to indicate the end of a method (if you need them, refactor the method! Go Vertical Formatting: -How big should a source file be? -The file length in lines should be around the size of 200-500 lines Horizontal Formatting: -How wide should a line be? - "you should never have to scroll to the right" -"I personally set my limit at 120 characters per line". Uncle Bob said - "Every software component should have one and only one responsibility.“ - Single Responsibility Principle always advocates higher cohesion and always recommends loose coupling Cohesion: is the degree to witch the various parts of a software component are related Coupling: is defined as the level of inter dependency between various software components Uncle Bob Definition - SRP - Single Responsibility Principle: “Every software component should have one and only one reason to change.” -Software entities should be open to extension but closed to modification, except to correct bugs. -“If a module is closed for modification and open for extension, we get the best of two worlds. Our code is both flexible and stable” What are the ways of extending a class? Generally, you achieve this by referring to abstractions for dependencies, such as interfaces or abstract classes, rather than using concrete classes Strategy: is a behavioral design pattern that lets you define a family of algorithms, put each of them into a separate class, and make their objects interchangeable -if class B is a subclass of class A, then wherever A is expected, B can be used instead -states that any class that is the child of a parent class should be usable in place of its parent without any unexpected behavior -This principle ensures that inheritance (one of the OOP principles) is used correctly - If an override method does nothing or just throws an exception, then you're probably violating the LSP -It can apply to inheritance or interface The four conditions for abiding by: Condition 1 Contravariance: the parameters of the overriding methods should be the same or more generic than the types of the parent’s method parameters Condition 2: Preconditions cannot be strengthened in the Subtype Any inherited method should not have more conditionals that change the return of that method, such as throwing an Exception Condition 3: Postconditions cannot be weakened in the Subtype Inherited methods should return the same type as that of their Parent (DB) Condition 4: Exception types must match Object-Oriented Design can violate the LSP: - Object-Oriented Design can violate the LSP - If a subclass throws an exception that is not defined in the superclass - There are any side effects in subclass methods that were Not part of the superclass definition Covariance: - You can override a method with the same signature but return a subclass of the object Returned - In another words, a method in a subclass can return an object whose type is a subclass of the type returned by the method with the same signature in the superclass - “Clients should not be forced to depend upon interfaces that they do not use.” -The goal of this principle is to reduce the side effects of using larger interfaces by breaking application interfaces into smaller ones - no class should be forced to implement any method(s) of an interface they don’t use - high-level modules should not depend on low-level modules; both should depend on abstractions. Abstractions should not depend on details. Details should depend upon abstractions - One of the ways to achieve the Open-Close Principle is to use the Dependency Inversion Principle -is considered a design pattern and not a framework. It's one way of implementing a more general software concept called Inversion of Control (IoC) - We used the Dependency Injection (DI) technique to implement the Dependency Inversion Principle (DIP), to apply the Open-Close Principle (OCP) Inversion of Control (IoC): is basically used to invert different kinds of additional responsibilities of a class rather than the main responsibility different types of dependency injection Constructor Injection: Dependency is passed to the object via its constructor that accepts an interface as an Argument Example: Interface injection: An interface provides an injector method that is responsible for injecting the dependency to any class that may require it Example: Setter injection: The dependent class has a public setter method through which the dependency is Injected Example: Advantages of dependency injection • Makes testing easier. • Reduces coupling between client and dependency classes. • The code is easier to maintain, reuse and extend best wishes