SoFunction
Updated on 2025-04-13

Tips and Practices to Improve Code Quality with C#

1. Guard Clause

The ward statement is used to deal with special situations in advance, avoid deep nested conditional judgments, and make the code logic clearer.

Traditional nesting writing

public string ProcessOrder(int quantity, double price, double discount)
{
    if (quantity > 0)
    {
        if (price > 0)
        {
            if (discount >= 0)
            {
                double total = quantity * price * (1 - discount);
                return $"Total cost: {total}";
            }
            else
            {
                return "Discount must be non-negative";
            }
        }
        else
        {
            return "Price must be positive";
        }
    }
    else
    {
        return "Quantity must be positive";
    }
}

Improved using harbor statement

public string ProcessOrder(int quantity, double price, double discount)
{
    // Wei sentence: Check for special circumstances in advance    if (quantity <= 0)
        return "Quantity must be positive";
    if (price <= 0)
        return "Price must be positive";
    if (discount < 0)
        return "Discount must be non-negative";

    // Main logic: No nesting required    double total = quantity * price * (1 - discount);
    return $"Total cost: {total}";
}

advantage:

  • Reduce nesting levels and make the code easier to read.
  • Handle exceptions in advance, and the logic is clearer.

2. Replace nested conditions with enumeration

Enumerations can be used to replace nested conditional judgments in certain scenarios, especially when there are multiple fixed states or types in the code.

Traditional nesting writing

public string GetPermissionLevel(string role)
{
    if (role == "admin")
    {
        return "Full access";
    }
    else if (role == "editor")
    {
        return "Edit access";
    }
    else if (role == "viewer")
    {
        return "View access";
    }
    else
    {
        return "No access";
    }
}

Improvements to use enumeration

public enum Role
{
    Admin,
    Editor,
    Viewer
}

public string GetPermissionLevel(Role role)
{
    switch (role)
    {
        case :
            return "Full access";
        case :
            return "Edit access";
        case :
            return "View access";
        default:
            return "No access";
    }
}

advantage:

  • Enumeration values ​​have clear semantics, avoiding hard-coded strings.
  • Reduce nested condition judgments and make the code more concise.

3. Use dictionary mapping to further optimize

If the behavior corresponding to each enum value is fixed, a dictionary can be used to further simplify the logic.

Improved using dictionary mapping

public enum Role
{
    Admin,
    Editor,
    Viewer
}

public class PermissionManager
{
    private static readonly Dictionary<Role, string> PermissionLevels = new Dictionary<Role, string>
    {
        { , "Full access" },
        { , "Edit access" },
        { , "View access" }
    };

    public string GetPermissionLevel(Role role)
    {
        if ((role, out var permissionLevel))
        {
            return permissionLevel;
        }
        return "No access";
    }
}

advantage:

  • Completely eliminate nested condition judgment.
  • When adding a new role, you only need to update the dictionary without modifying the function logic.

4. The Single Responsibility Principle (SRP)

Each function or class should be responsible for only one task, which can improve the readability, maintainability and testability of the code.

Before improvement

public string ProcessOrder(int quantity, double price, double discount)
{
    if (quantity <= 0)
        return "Quantity must be positive";
    if (price <= 0)
        return "Price must be positive";
    if (discount < 0)
        return "Discount must be non-negative";
    double total = quantity * price * (1 - discount);
    return $"Total cost: {total}";
}

After improvement

public class OrderProcessor
{
    public void ValidateInput(int quantity, double price, double discount)
    {
        if (quantity <= 0)
            throw new ArgumentException("Quantity must be positive");
        if (price <= 0)
            throw new ArgumentException("Price must be positive");
        if (discount < 0)
            throw new ArgumentException("Discount must be non-negative");
    }

    public double CalculateTotal(int quantity, double price, double discount)
    {
        return quantity * price * (1 - discount);
    }

    public string ProcessOrder(int quantity, double price, double discount)
    {
        ValidateInput(quantity, price, discount);
        double total = CalculateTotal(quantity, price, discount);
        return $"Total cost: {total}";
    }
}

advantage:

  • Each function does only one thing and has clear responsibilities.
  • Easier to test and reuse.

5. Avoid duplicate code (DRY - Don’t Repeat Yourself)

Repeating code will increase maintenance costs and easily introduce errors. Repetition can be avoided by extracting public logic into functions or tool classes.

Before improvement

public double CalculateAreaOfSquare(double side)
{
    return side * side;
}

public double CalculateAreaOfRectangle(double length, double width)
{
    return length * width;
}

After improvement

public double CalculateArea(string shape, params double[] dimensions)
{
    switch (shape)
    {
        case "square":
            return dimensions[0] * dimensions[0];
        case "rectangle":
            return dimensions[0] * dimensions[1];
        default:
            throw new ArgumentException("Unsupported shape");
    }
}

advantage:

  • Reduce duplicate code and make the logic more concentrated.
  • It's easier to expand new features.

6. Use meaningful naming

The naming of variables, functions and classes should clearly express their purpose, avoiding the use of ambiguity or abbreviation.

Before improvement

public double Calc(double a, double b)
{
    return a * b;
}

After improvement

public double CalculateArea(double length, double width)
{
    return length * width;
}

advantage:

  • The code is easier to read and reduces the cost of understanding.
  • Reduce the necessity of comments.

7. Use exception handling

Rationally using exception handling can improve the robustness of the code and avoid program crashes.

Before improvement

public double Divide(double a, double b)
{
    return a / b; // If b is 0, an exception will be thrown}

After improvement

public double Divide(double a, double b)
{
    if (b == 0)
        throw new DivideByZeroException("Division by zero is not allowed");
    return a / b;
}

advantage:

  • Clearly handle exceptions to avoid unexpected errors.
  • Improve code reliability.

8. Write unit tests

Unit testing ensures the correctness of the code and provides security when modifying the code.

Example

using ;

[TestClass]
public class MathOperationsTests
{
    [TestMethod]
    public void TestAdd()
    {
        (5, Add(2, 3));
        (0, Add(-1, 1));
    }

    public int Add(int a, int b)
    {
        return a + b;
    }
}

advantage:

  • Make sure the code is correct.
  • Supports refactoring and continuous integration.

9. Use design mode

Design patterns are a classic solution to common problems that can improve the scalability and maintainability of your code.

Example: Factory Mode

public interface IAnimal
{
    string Speak();
}

public class Dog : IAnimal
{
    public string Speak()
    {
        return "Woof!";
    }
}

public class Cat : IAnimal
{
    public string Speak()
    {
        return "Meow!";
    }
}

public class AnimalFactory
{
    public static IAnimal CreateAnimal(string type)
    {
        switch (type)
        {
            case "dog":
                return new Dog();
            case "cat":
                return new Cat();
            default:
                throw new ArgumentException("Unknown animal type");
        }
    }
}

// usevar dog = ("dog");
(()); // Output: Woof!

advantage:

  • Creation and use of decoupled objects.
  • Improve code flexibility.

10. Code comments and documentation

Good comments and documentation can help others understand the intent and implementation details of the code.

Example

/// &lt;summary&gt;
/// Calculate the rectangle area./// &lt;/summary&gt;
/// <param name="length">Length of rectangle</param>/// <param name="width">Width of rectangle</param>/// <returns> Area of ​​the rectangle</returns>public double CalculateArea(double length, double width)
{
    return length * width;
}

advantage:

  • Improve the readability of the code.
  • Convenient team collaboration and maintenance.

11. Use version control tools

Use version control tools such as Git to track code changes for easy collaboration and rollback.

Example

git init
git add .
git commit -m "Initial commit"

advantage:

  • Record code history for easy backtracking.
  • Support team collaborative development.

12. Code Refactoring

Regularly refactor the code, optimize structure and performance, and maintain the healthy state of the code.

Before improvement

public List<int> ProcessData(List<int> data)
{
    List<int> result = new List<int>();
    foreach (var item in data)
    {
        if (item % 2 == 0)
        {
            (item * 2);
        }
    }
    return result;
}

After improvement

public List<int> ProcessData(List<int> data)
{
    return (item => item % 2 == 0).Select(item => item * 2).ToList();
}

advantage:

  • The code is more concise and the performance is better.
  • Reduce potential errors.

Summarize

The following tips can significantly improve code quality:

  1. Wei's sentence
  2. Replace nested conditions with enumeration
  3. Using dictionary mapping
  4. Single responsibility principle
  5. Avoid duplicate code
  6. Use meaningful naming
  7. Use exception handling
  8. Writing unit tests
  9. Use design mode
  10. Code comments and documentation
  11. Use version control tools
  12. Code Refactoring

Combining these techniques, you can write high-quality, easy-to-maintain code.

This is the end of this article about the skills and practices of using C# to improve code quality. For more related content on improving code quality in C#, please search for my previous articles or continue browsing the related articles below. I hope everyone will support me in the future!