By doing some research, it seems that people generally agree that the arguments of public methods should be checked, and private functions should not. This causes me some questions, but so far I have not been able to find a satisfactory answer.
Example:
public void DoSomething(int i) { if (i < 0) throw new ArgumentOutOfRangeException("i"); double d = DoWork(i); } private double DoWork(int i) { double ret = ...;
Thoughts:
What if requirement i non-negative changes inside DoWork() ? The project risks leaving outdated verification checks in place. The programmer is responsible for setting up the use of a function that has changed, I know, but I'm not interested in whether there is a better way to minimize the risk of error.
What about different calls to DoWork() not from DoSomething() ? Should we check the arguments redundantly?
public void DoSomething(int i) { if (i < 0) throw new ArgumentOutOfRangeException("i"); double d = DoWork(i); } public void DoSomethingElse() { int i = 5; if (i < 0) throw new ArgumentOutOfRangeException("i"); double d = DoWork(i); } private double DoWork(int i) { double ret = ...;
This can be cleared up a bit by putting a check in its own function. Then there is a risk that a new function that calls DoWork(int i) will forget to confirm i .
public void DoSomething(int i) { ThrowIfIntegerIsNegative(i); double d = DoWork(i); } public void DoSomethingElse() { int i = 5; ThrowIfIntegerIsNegative(i); double d = DoWork(i); } static void ThrowIfIntegerIsNegative(int i) { if (i < 0) throw new ArgumentOutOfRangeException("i"); } private double DoWork(int i) { double ret = ...;
Is it really better?
public void DoSomething(int i) { double d = DoWork(i); } public void DoSomethingElse() { double d = DoWork(5); } private double DoWork(int i) { if (i < 0) throw new ArgumentOutOfRangeException("i"); double ret = ...;
Depending on the situation, these are some of the goals that I am trying to achieve at the same time:
- Test the arguments in one place (and possibly inside the function using the argument)
- Report the error sooner rather than later (you probably donβt want the heap of code to run for an hour, just to not work at the end for incorrect user input)
- Avoid checking arguments multiple times
- Avoid Performance Impacts in Release Code
How do you make a balance? Which methodology is best for you? I would really appreciate your understanding.
source share