Developers write code. Unfortunately, developers also write defects, most of whom are added in the initial coding phase. Fixed places where these defects have the low cost is also the initial stage of development. If you wait until a function test or system test to capture and repair the defect, then your software development cost will be much higher. In this article, the author Scott Will, TED Rivera and Adam Tate discusses some basic "defensive" codes and unit test practices to make developers easier to find defects - more importantly, from the beginning to prevent defects. Defensive driving and defensive development
Most drivers receive the education of defensive driving technology - this has a good reason - but not all developers have accepted the education of defensive development, especially those who have not used assembly language (if not If you haven't used it at all, you have not cared for a young developer who wrote extremely compact code due to memory constraints and processor restrictions. This article discusses defensive coding and unit testing concepts, which can help developers generate better code faster and less defects. Why is defensive development important? The best position for capturing errors, problems, and defects is in the early days of the development cycle. Figure 1 shows the most prone to defects, as well as where they are easily discovered, and include the cost of repairing these defects (these costs are for 1996 - today's cost is obviously higher).
Figure 1. Defect: introduction phase and discovery phase (including cost)
Of course, it is better than finding defects in the coding phase to prevent them at the beginning. Preventing defects should be the most prioritized developers. We will analyze several simple and proven methods that allow developers to prevent and detect defects when coding and unit testing. The most effective way to prevent defects (especially systemic defects) before compiling (defensive design) is to carefully check the design of the coding. Defects caused by design defects - although it is generally not a lot of - usually patch costs are the highest. The time beforehand is very small for the following points to check the design for a significant long-term return. Design Considering whether there is any unclear or confusing part? If so, clarify these issues before writing any code. Otherwise, you may explain a design demand in one way, and colleagues explain it in another way, thereby getting incompatible implementation. If your code wants to access data accessed by other components, then ensure that your design can handle this situation. At the same time, check the security issues for design. If your code is seriously dependent on the code of other applications, then do you familiar with the design to check the design? Consider joining a developer who is familiar with the product in your design inspection team. Integration issues found during the design phase can be processed. Installation and Use Consider if your code is an upgrade of previous versions, then does it make the parameters or other options that fail to fail? What other products are interacting with new code or integration - if these products itself changed? Also, is your code easy to install? How does your code run on a new version of the operating system or database? Do you know which changes have been added to these new versions and whether they (and how) affect your code? Is this just the test design combined tester? Although you may think that tested problems are not what you need to care, but in fact unit test is one of the responsibilities of developers - almost all anything that makes execution function testing and / or system testing will make unit testing more Easy to perform. Below is a few examples of tested domain content.
Whether to design whether the external tool is allowed to access the "Status" variable (for example, the current state), especially those that need to verify whether the code is working correctly to help determine the problem. Is it paying enough attention to tracking and logs? You make others analyzing defects, your easier after you find defects (and find your own problems in unit test). Do you consider all contexts that may call your code? If you can associate the error message with the user function context called it, the user is more likely to understand this error. Does design a specific "hook" that you need for your test automation tool? Think more, you can do more content in this list, especially those for your products or organization specific content. Defensive Coding Technology: The compiler is your friend when you complete the design inspection, it is called. Let us face it, except for design errors, the code is the only place to introduce defects. In any case, your test procedure and customer will not join the defect - only you will. We all know that time is very nervous, but if you don't have time to write it correctly, how can you find time to fix it? It takes some time, which will make you easier in future coding work. One of the best way to prevent defects is to use the compiler. Fear is that developers often choose to use the minimum warning output when compiling, so enabate all warnings that compile-handle even if the compiler is configured to check all aspects, do not generate a warning as a write code A challenge. In addition, using multiple compilers to make many programmers benefit - this method sometimes captures different syntax errors. Coding habits Let's introduce a few good coding habits. We are not to define "Best Code Habits" - we just want to form your own code to write habits. Here are a few examples of the best habits for reference. Initialization All variables before use Do you have a set of acceptable default, especially for data that may be modified by the user, other components, or other programs? At the same time, we strongly ask you to list all local variables to be used in the outer circumference process, and then initialize them. This will not leave any questions when you write the code. Although this may take some time and add a few lines of code like there is no reason, most of the optimized compiler does not generate any of this compared to just "on the fly" declaration. Additional runtime code. Listing 1 shows an example of the initial number of code in one routine: Listing 1. Initializing local variables Public unsigned short transmogrify (ufeventlink incominglink)
{
//
// Local Variables
//
UNSIGNED SHORT USRC;
String SoureventType;
String StheireventType;
//
// Beginning of Code
//
USRC = 0;
SoureventType = NULL;
StheireventType = NULL;
//
// a miracle occurs ...
//
Return (USRC);
} // end "transmogrify"
Use a "encoding standard" document if you have an encoded standard documentation, use it. You can find many coding standards on the Internet. Find a simple, cutting key, and leave a certain activity space for you. Sun's website has an article about Java programming coding specifications (see Resources), which gives the following reasons for the following reasons: a cost of 80% of the software survival is used in maintenance. Almost no software is maintained by the original authors throughout the use. The coding specification improves the software readability, allowing engineers to understand new code faster and more fully. If you deliver the source code as product, then you need to ensure that it is equipped with all other products you created. Even if the "standard" idea is not approved, at least this simple suggestion: Use the Hungarian Name Act to the variable name, which will make your code easier to read and maintain (. Guarantee that the consistency of the return code is in debugging) The situation that will make a hassle is: Call program mask (or overwrite) a return code indicating an error. Be sure to return what value to return to the routine that calls your code and guaranteed from the routine you call All error codes are properly processed. If you return code N means one thing, don't indicate another thing in other places. Use the "single point exit" for each routine. How to emphasize nor too: Exit for each routine - means that there is no multiple returns! This is the most easily ignored, and it is the best habit you can use. If the routine is only returned from one place, Then use a very easy way to ensure that all necessary cleaning work is completed before returning, which makes debugging easier. Listing 2 shows an example of code containing multiple returns. Pay attention to duplicate code, and even forget the "cleanup" project How easy is it. List 2. Single point exit example 1 public string getName ()
2 {
3 //
4 // Local Variables
5 //
6 string returbtring;
Seduce
8
9 //
10 // Beginning of Code
11//
12 returbtring = textfield.gettext ();
13 IF (null == returbtring)
14 {
15 Badcount ;
16 TOTALCOUNT ;
17 Return (NULL)
18}
19
20 returnstring = returbtring.trim ();
21 if (Returnstring.equals ("))
twenty two {
23 Badcount ;
24 Totalcount ;
25 Return (NULL);
26}
27
28 TOTALCOUNT ;
29 return (returbtring);
30
31} // endname
At 15 lines, Badcount increased because getText () returns NULL. On the 23rd line, the Badcount code is repeated. Now I think if this example needs to complete more complex "cleaning". Listing 3 shows a better way: Listing 3. Single point exit example - after correction
1 public string getname ()
2 {
3 //
4 // Local Variables5 //
6 string returbtring;
Seduce
8
9 //
10 // Beginning of Code
11//
12 returbtring = textfield.gettext ();
13 IF (NULL! = Returbtring)
14 {
15 Returnstring = returbtring.trim ();
16 IF (Returnstring.equals ("))
17 returbtring = null;
18}
19
20 ////
21 // "Cleanup"
twenty two //
23 if (null == returbtring)
24 Badcount ;
25 TotalCount ;
26
27 return (returbtring);
Twist
29} // endname
This is a simplified example, but please pay attention to how easy it will be made in this habit, and the benefits of doing this.