Maintainability and Clean Code
Advanced Programming, Lecture 11
Advanced Programming, Lecture 11
Set of flashcards Details
| Flashcards | 29 | 
|---|---|
| Language | Deutsch | 
| Category | Computer Science | 
| Level | University | 
| Created / Updated | 26.03.2021 / 03.04.2021 | 
| Weblink | 
                             
                                
                                
                                https://card2brain.ch/cards/20210326_maintainability_and_clean_code
                             
                         | 
                    
| Embed | 
                            
                             
                                
                                
                                <iframe src="https://card2brain.ch/box/20210326_maintainability_and_clean_code/embed" width="780" height="150" scrolling="no" frameborder="0"></iframe>
                             
                         | 
                    
Maintainability
- degree of effectiveness and efficiency with which the product can be modified
 - consists of 
- Analysability
 - Modularity
 - Reusability
 - Modifiability
 - Testability
 
 
Why is Maintainability important?
- reduces costs during maintenance
 - enables other 7 characteristics of software product quality (security, functional suitability, performance)
 
How is Maintainability achieved?
- writing clean code
 - improves internal and external quality of product
 
Clean Code - Definition
- clear, understandable, comprehensible, logical and disciplined implementation of code
 - code is designed to be easy to read, change, expand and maintain
 
Conventions - Idea and Problem
Idea:
- improve readability by creating common look and feel
 
Problems:
- Conventions are ignored (no knowledge)
 - Conventions differ between languages and communities
 
Convention - English
Reasons for other Languages
- harder to write english commentaries/find names
 - bad english skills could lead to misunderstandings/typos
 
Reasons for using English:
- English communities are much larger
 - for help of english community, dont have to translate
 - no mixture of english programming language and local language
 - you should be able to read and speak fluent English
 
Convention - which to use
- use language default
- detailed guidelines available
 - style switches necessary when working on multiple projects within the same team or project with multiple languages
 
 - decide in your team on a standard
- keep consistent
 - one style over all languages
 - maybe switching styles between teams
 
 
Bad Smells - Definition
- indications of poor coding and design choices that may lead to bad maintainability
 - technically not incorrect
 - indicate weaknesses and could be slowing down development or increase risk of bugs
 - code vs architectural level
 
Bad Smells - Architectural Level
- Lack of Modularity: low cohesion, high coupling
 - God Class: uses many attributes of other classes, many big methods with high complexity, does everything
 - Refused Bequest: Subclasses dont need inherited methods and data from parents, subclass and superclass too different
 - Feature Envy: Method is more interested in data/functions of another class, envies scope of other class
 - Shotgun Surgery: single responsibility has been split up among large number of classes
 
Bad Smells - Code Level
- Simulated Polymorphism: conditionals are used instead of inheritance and polymorphism
 - Dead Code: code blocks are never reached, no longer used
 - Duplicated Code: same structure in more than one place, same expressions in two methods,...
 - Data Clumps: Identical group of variables passed from function to function together instead of one single data structure
 - Primitive Obsession: use of primitives to represent domain idea instead of self-defined, meaningful types (Currency, telephone number)
 
Refactoring - Definition
- changing a software system in such a way that it doesnt alter external behavior of code but improves internal structure
 
Refactoring - Advantages
- improve software design
 - make software easier to understand and modify
 - helps finding bugs by improving general understandability of the code
 - program faster
 
Refactoring:
You have a code fragment that could be grouped together
Extract Function
- turn it into own function
 - replace extracted code with new method call
 
Refactoring:
A function is used by more features of another class than by its own class
Move Function
- in other class create function with similar body
 - turn old function into delegation or remove old function
 
Refactoring:
type code which affects class behaviour, but subclassing not possible
State/Strategy:
- replace type code with state object
 - create new state class for type code
 - add subclass of state object for each type code
 
Refactoring:
Two functions with very similar logic but different literal values
Parameterization
- use single function and parameterize it
 - use one of similar functions as baseline
 - replace original calls with calls to parameterized function
 
Refactoring:
Several sublasses have methods that perfom nearly identical work
Pull up method
- make methods identical and move them to superclass
 - parameterize them
 - delete sublcass methods
 
Refactoring:
subclass and its parent are no longer different enough to be worth keeping separate
Collapse Hierarchy
- Merge subclass and superclass to one class
 - adjust references and remove empty class
 
Unit Tests - Placement
- Unit Testing
- testing the smallest testable parts (public methods, APIs)
 - do units fulfill functionalities
 
 - Integration Testing
- testing groups of units across modules
 - do units perform correctly together
 
 - System Testing
- testing entire application as whole
 - does system meet specification
 
 - Acceptance Testing
- testing final system before release
 - are end users expectations met
 
 
Unit Tests - Definition
- automated piece of code that invokes unit of work being tested
 - checks assumptions about single end result of that unit
 - consistent in results if production code doesnt change
 
Unit Tests - Important Properties
- Self-Documenting and Readable: clear, precise and easy to understand, expressive with clear intent
 - Concept-bounded: should test single concept only, asserts should be minimized
 - Isolated: tested unit should be isolated from external dependencies (databases)
 
Unit Tests - FIRST
- properties of clean tests
 - Fast: tests should run quickly, otherwise they are not run frequently
 - Independent: tests should not depend on each other, could cause stream of failure
 - Repeatable: tests should not rely on environment, always yield same result for same code base
 - Self-Validating: boolean output
 - Timely: write tests before production code
 
Test Driven Development
- Write a for now failing test for a piece of functionality
 - Write production code that passes test
 - Refactor, run all tests to verify refactoring did not change external behaviour
 
Stubs
- controllable replacement for an existing dependency in the system
 - used to test code depending on external objects, without dealing with dependency directly
 - find interface that object under test works against
 - eventually add level of indirection hiding interface
 - replace underlying implementation of interface with something you have control over (stub)
 
Mocks
- fake object in system that decides whether unit test fails or passes
 - verifies whether object under test called the fake object as expected
 - class under test communicates with mock, mock records all communication
 - test uses mock object to check if test passed based on verifying communication using expectations
 
Fakes
- either mock (tested against) or stub (tested against object under test)
 - main purposes:
- test independence
 - interface discovery: stubbing/mocking not yet existent classes
 
 
Fixtures
- fixed state that exists at start of the test
 - ensures that test is repeatable by ensuring all preconditions
 - fixture might be setup/torn down after test
 
Four Phases of a Unit Test
- Set up Fixture
 - Exercise System under test: interact with SUT to exercise the behavior that should be verified
 - Result Verification: determine whether outcome fails the test or not
 - Fixture Teardown: put everything back into original state
 
Unit Tests - Advantages
- allows programmer to refactor code at later time and make sure that modules still work correctly
 - by testing parts of program first and then sum of its parts integration testing becomes much easier