Debug.Assert vs Exception Throwing - c#

I've read plenty of articles (and a couple of other similar questions that were posted on StackOverflow) about how and when to use assertions, and I understood them well. But still, I don't understand what kind of motivation should drive me to use Debug.Assert instead of throwing a plain exception. What I mean is, in .NET the default response to a failed assertion is to "stop the world" and display a message box to the user. Though this kind of behavior could be modified, I find it highly annoying and redundant
to do that, while I could instead, just throw a suitable exception. This way, I could easily write the error to the application's log just before I throw the exception, and plus, my application doesn't necessarily freeze.
So, why should I, if at all, use Debug.Assert instead of a plain exception? Placing an assertion where it shouldn't be could just cause all kinds of "unwanted behavior", so in my point of view, I really don't gain anything by using an assertion instead of throwing an exception. Do you agree with me, or am I missing something here?
Note: I fully understand what the difference is "in theory" (Debug vs Release, usage patterns etc.), but as I see it, I would be better off throwing an exception instead of performing an assert. Since if a bug is discovered on a production release, I still would want the "assertion" to fail (after all, the "overhead" is ridiculously small), so I'll be better off throwing an exception instead.
Edit: The way I see it, if an assert failed, that means that the application entered some kind of corrupted, unexpected state. So why would I want to continue execution? It doesn't matter if the application runs on a debug or release version. The same goes for both

Though I agree that your reasoning is plausible -- that is, if an assertion is violated unexpectedly, it makes sense to halt execution by throwing -- I personally would not use exceptions in the place of assertions. Here's why:
As others have said, assertions should document situations that are impossible, in such a manner that if the allegedly impossible situation comes to pass, the developer is informed. Exceptions, by contrast, provide a control flow mechanism for exceptional, unlikely, or erroneous situations, but not impossible situations. For me, the key difference is this:
It should ALWAYS be possible to produce a test case which exercises a given throw statement. If it is not possible to produce such a test case then you have a code path in your program which never executes, and it should be removed as dead code.
It should NEVER be possible to produce a test case which causes an assertion to fire. If an assertion fires, either the code is wrong or the assertion is wrong; either way, something needs to change in the code.
That's why I would not replace an assertion with an exception. If the assertion cannot actually fire, then replacing it with an exception means you have an untestable code path in your program. I dislike untestable code paths.

Assertions are used to check the programmer's understanding of the world. An assertion should fail only if the programmer has done something wrong. For example, never use an assertion to check user input.
Asserts test for conditions that "cannot happen". Exceptions are for conditions that "should not happen but do".
Assertions are useful because at build time (or even run time) you can change their behavior. For example, often in release builds, the asserts aren't even checked, because they introduce unneeded overhead. This is also something to be wary of: your tests may not even be executed.
If you use exceptions instead of asserts, you lose some value:
The code is more verbose, since testing and throwing an exception is at least two lines, while an assert is only one.
Your test and throw code will always run, while asserts can be compiled away.
You lose some communication with other developers, because asserts have a different meaning than product code that checks and throws. If you are really testing a programming assertion, use an assert.
More here: http://nedbatchelder.com/text/assert.html

EDIT:
In response to the edit/note you made in your post:
It sounds like using exceptions are the right thing to use over using assertions for the type of things you are trying to accomplish.
I think the mental stumbling block you are hitting is that you are considering exceptions and assertions to fulfill the same purpose, and so you are trying to figure out which one would be 'right' to use. While there may be some overlap in how assertions and exceptions can be used, don't confuse that for them being different solutions to the same problem- they aren't. Assertions and Exceptions each have their own purpose, strengths, and weaknesses.
I was going to type up an answer in my own words but this does the concept better justice than I would have:
C# Station: Assertions
The use of assert statements can be an
effective way to catch program logic
errors at runtime, and yet they are
easily filtered out of production
code. Once development is complete,
the runtime cost of these redundant
tests for coding errors can be
eliminated simply by defining the
preprocessor symbol NDEBUG [which
disables all assertions] during
compilation. Be sure, however, to
remember that code placed in the
assert itself will be omitted in the
production version.
An assertion is best used to test a
condition only when all of the
following hold:
* the condition should never be false if the code is correct,
* the condition is not so trivial so as to obviously be always true, and
* the condition is in some sense internal to a body of software.
Assertions should almost never be used to detect situations that arise
during software's normal operation.
For example, usually assertions should
not be used to check for errors in a
user's input. It may, however, make
sense to use assertions to verify that
a caller has already checked a user's
input.
Basically, use exceptions for things that need to be caught/dealt with in a production application, use assertions to perform logical checks that will be useful for development but turned off in production.

I think a (contrived) practical example may help illuminate the difference:
(adapted from MoreLinq's Batch extension)
// 'public facing' method
public int DoSomething(List<string> stuff, object doohickey, int limit) {
// validate user input and report problems externally with exceptions
if(stuff == null) throw new ArgumentNullException("stuff");
if(doohickey == null) throw new ArgumentNullException("doohickey");
if(limit <= 0) throw new ArgumentOutOfRangeException("limit", limit, "Should be > 0");
return DoSomethingImpl(stuff, doohickey, limit);
}
// 'developer only' method
private static int DoSomethingImpl(List<string> stuff, object doohickey, int limit) {
// validate input that should only come from other programming methods
// which we have control over (e.g. we already validated user input in
// the calling method above), so anything using this method shouldn't
// need to report problems externally, and compilation mode can remove
// this "unnecessary" check from production
Debug.Assert(stuff != null);
Debug.Assert(doohickey != null);
Debug.Assert(limit > 0);
/* now do the actual work... */
}
So as Eric Lippert et al have said, you only assert stuff that you expect to be correct, just in case you (the developer) accidentally used it wrong somewhere else, so you can fix your code. You basically throw exceptions when you have no control over or cannot anticipate what comes in, e.g. for user input, so that whatever gave it bad data can respond appropriately (e.g. the user).

Another nugget from Code Complete:
"An assertion is a function or macro
that complains loudly if an assumption
isn't true. Use assertions to document
assumptions made in code and to flush
out unexpected conditions. ...
"During development, assertions flush
out contradictory assumptions,
unexpected conditions, bad values
passed to routines, and so on."
He goes on to add some guidelines on what should and should not be asserted.
On the other hand, exceptions:
"Use exception handling to draw
attention to unexpected cases.
Exceptional cases should be handled in
a way that makes them obvious during
development and recoverable when
production code is running."
If you don't have this book you should buy it.

Debug.Assert by default will only work in debug builds, so if you want to catch any sort of bad unexpected behavior in your release builds you'll need to use exceptions or turn the debug constant on in your project properties (which is considered in general not to be a good idea).

Use assertions for things which ARE possible but should not happen (if it were impossible, why would you put an assertion?).
Doesn't that sound like a case to use an Exception? Why would you use an assertion instead of an Exception?
Because there should be code that gets called before your assertion that would stop the assertion's parameter being false.
Usually there is no code before your Exception that guarantees that it won't be thrown.
Why is it good that Debug.Assert() is compiled away in prod? If you want to know about it in debug, wouldn't you want to know about it in prod?
You want it only during development, because once you find Debug.Assert(false) situations, you then write code to guarantee that Debug.Assert(false) doesn't happen again.
Once development is done, assuming you've found the Debug.Assert(false) situations and fixed them, the Debug.Assert() can be safely compiled away as they are now redundant.

Suppose you are a member of a fairly large team and there are several people all working on the same general code base, including overlapping on classes.
You may create a method that is called by several other methods, and to avoid lock contention you do not add a separate lock to it, but rather "assume" it was previously locked by the calling method with a specific lock.
Such as,
Debug.Assert(RepositoryLock.IsReadLockHeld || RepositoryLock.IsWriteLockHeld);
The other developers might overlook a comment that says the calling method must use the lock, but they cannot ignore this.

Related

Handling the usual errors: If-Then-Throw blocks vs. Code Contracts vs. an Assert class

When I start writing a method, I usually check for exceptional conditions first in the method, using If-Then-Throw blocks.
public void ReadFile(string filePath)
{
if (string.IsNullOrEmpty(filePath)
{
throw new ArgumentException(...
This style seems to be very clear and easy to understand, but it takes up more space than I think is necessary. I want to be able to handle errors and exceptional conditions in a smart way that enables whoever's reading these errors to easy take care of them while also keeping the code itself clean.
I've looked a bit at Code Contracts, which seems to me a requirement for certain conditions before and after a method's execution. That seems to be a tad bit overkill for just a null string, and I'm not sure if you can have contract clauses within the method itself, for instance, if the path is not null but no file exists at that path.
The solution I'm thinking of using is rolling my own Assert class. This class will basically turn the above If-Then-Throw into a simple one liner.
Assert.IsFalse<ArgumentException>(string.IsNullOrEmpty(filePath), "The path cannot be null or empty.");
All Assert methods would throw an exception using the exception type and the message in the last argument. The thing is that I'm not sure if this is good practice. Does it confuse what exceptions are truly for, or what Assert actually means? Would it make error-handling easier or harder?
I would say this is not good practice. As you pointed out, this would confuse the roles of Assertions and Exceptions. The topic is somewhat common, this link has a lot of nice ideas. By combining exceptions and assertions, you end up with a conundrum... is the class an exception helper, or is it an assertion helper?
Since assertions are compiled out of the Release build, would your assertion class even work in Release mode? It would be non-conventional to expect an Assertion class to work in release mode. So, would your Assertion class throw the exceptions in Release mode? There lies the confusion. By convention, I would say the exception should not be thrown when using an Assert Class (in Release mode) because it is understood that assertions are not part of a Release build.
The code above should not make 'Exception Handling' easier nor harder, it should be the same since the exception handling depends on what is catching the exception in the stack. I think you are really asking if it makes throwing Exceptions easier or harder. I think it could make dealing with your exceptions easier. I also think it is probably unnecessary. What is most important is that you are consistent with this... if you are going to use an ExceptionHelper class, then embrace it and be consistent... otherwise it is all done for naught.
Debug.Assert:
Use liberally
Use whenever there is a chance that an assumption could be wrong
Used to help other programmers, not necessarily the end user
Should never affect the flow of the program
Not compiled in Release builds
Always yells 'BLOODY MURDER' when something unexpected happens, this is a good thing
many other reasons, I'm not aiming for a complete list
Exceptions:
Can be caused for any reason, it is not always known why
Always in debug or release builds
Pertains to how the application flows
Some exception handlers may silently swallow an exception and you would never know it
many other reasons, I'm not aiming for a complete list
To be honest, I'm not sure a custom Assert class would help clarify anything, and I'm not sure you should be worried about two lines need to check and throw an exception vs one line. Your current way of checking parameters is the way we do things as well. In fact, a majority of public methods around our code look something like this:
public void PerformStringOperation(string str1, string str2)
{
if(string.IsNullOrEmpty(string1))
throw new ArgumentNullException(...);
if(string.IsNullOrEmpty(string2))
throw new ArgumentNullException(...);
// perform string operation(s) here
}
We have never found it too encumbering, and I'm sure it is the exact solution used by many teams.

Is this code defensive programming, or bad practice? [closed]

Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 5 years ago.
The community reviewed whether to reopen this question 9 months ago and left it closed:
Original close reason(s) were not resolved
Improve this question
I have this debate with my colleague about this piece of code:
var y = null;
if (x.parent != null)
y = x.parent.somefield;
My point of view is that in the place where the code is, x.parent should not POSSIBLY be null. And when it is null, we have a serious problem and I want to know it! Hence, the null check should not be there and let the down stream exception happen.
My colleague says this is defensive programming. And the null check makes sure the code doesn't break the application.
My question is, is this defensive programming? Or a bad practice?
Note: the point is not who is right. I'm trying to learn from this example.
It looks like your colleague is misunderstanding "defensive programming" and/or exceptions.
Defensive Programming
Defensive programming is about protecting against certain kinds of errors.
In this case x.parent == null is an error because your method needs to use x.parent.SomeField. And if parent were null, then the value of SomeField would clearly be invalid. Any calculation with or task performed using an invalid value would yield erroneous and unpredictable results.
So you need to protect against this possibility. A very good way to protect is by throwing a NullPointerException if you discover that x.parent == null. The exception will stop you from getting an invalid value from SomeField. It will stop you doing any calculations or performing any tasks with the invalid value. And it will abort all current work up until the the error is suitably resolved.
Note the exception is not the error; an invalid value in parent that is the actual error. The exception is in fact a protection mechanism. Exceptions are a defensive programming technique, they're not something to be avoided.
Since C# already throws an exception, you don't actually have to do anything. In fact it turns out that your colleague's effort "in the name of defensive programming", is actually undoing built-in defensive programming provided by the language.
Exceptions
I've noticed many programmers are unduly paranoid about exceptions. An exception itself isn't an error, it's simply reporting the error.
Your colleague says: "the null check makes sure the code doesn't break the application". This suggests he believes that exceptions break applications. They generally don't "break" an entire application.
Exceptions could break an application if poor exception handling puts the application in an inconsistent state. (But this is even more likely if errors are hidden.) They can also break an application if an exception 'escapes' a thread. (Escaping the main thread obviously implies your program has terminated rather ungracefully. But even escaping a child thread is bad enough that the best option for an operating system is to GPF the application.)
Exceptions will however break (abort) the current operation. And this is something they must do. Because if you code a method called DoSomething which calls DoStep1; an error in DoStep1 means that DoSomething cannot do its job properly. There is no point in going on to call DoStep2.
However, if at some point you can fully resolve a particular error, then by all means: do so. But note the emphasis on "fully resolve"; this doesn't mean just hide the error. Also, just logging the error is usually insufficient to resolve it. It means getting to the point where: if another method calls your method and uses it correctly, the 'resolved error' will not negatively affect the caller's ability to do its job properly. (No matter what that caller may be.)
Perhaps the best example of fully resolving an error is in the main processing loop of an application. Its job is to: wait for a message in the queue, pull the next message off the queue and call appropriate code to process the message. If an exception was raised and not resolved before getting back to the main message loop, it needs to be resolved. Otherwise the exception will escape the main thread and the application will be terminated.
Many languages provide a default exception handler (with a mechanism for the programmer to override/intercept it) in their standard framework. The default handler will usually just show an error message to the user and then swallow the exception.
Why? Because provided you haven't implemented poor exception handling, your program will be in a consistent state. The current message was aborted, and the next message can be processed as if nothing is wrong. You can of course override this handler to:
Write to log file.
Send call-stack information for troubleshooting.
Ignore certain classes of exception. (E.g. Abort could imply you don't even need to tell the user, perhaps because you previously displayed a message.)
etc.
Exception Handling
If you can resolve the error without an exception first being raised, then it is cleaner to do so. However, sometimes the error cannot be resolved where it first appears, or cannot be detected in advance. In these cases an exception should be raised/thrown to report the error, and you resolve it by implementing an exception handler (catch block in C#).
NOTE: Exception handlers server two distinct purposes: First they provide you a place to perform clean-up (or rollback code) specifically because there was an error/exception. Second, they provide a place to resolve an error and to swallow the exception. NB: It's very important in the former case that the exception be re-raised/thrown because it has not been resolved.
In a comment about throwing an exception and handling it, you said: "I wanted to do that but I was told it creates exception handling code everywhere."
This is another misconception. As per the previous side-note you only need exception handling where:
You can resolve an error, in which case you're done.
Or where you need to implement rollback code.
The concern may be due to flawed cause-and-effect analysis. You don't need rollback code just because you're throwing exceptions. There are many other reasons that exceptions can be thrown. Rollback code is required because the method needs to perform clean-up if an error occurs. In other words the exception handling code would be required in any case. This suggests the best defence against excessive exception handling is to design in such a way that the need for clean-up on errors is reduced.
So don't "not throw exceptions" to avoid excessive exception handling. I agree excessive exception handling is bad (see design consideration above). But it is far worse to not rollback when you should because you didn't even know there was an error.
Interesting question. From my point of view, whether or not to include the check is a matter of how well the data is validated, where does it come from and what can happen when the check fails.
"x.parent should not POSSIBLY be null" is a serious assumption. You need to be very sure of it to play safe, of course there is the classic "it will never happen"....... until it happens, that's why I think it's interesting to review the possibilities.
I see two different things to think about.
Where does the data comes from?
If it comes from another method in the same class, or from some related class, since you have more or less full control about it, it's logical to relax your defenses, as you can reasonably assume that it's very unlikely to have bad data to begin with, or if it happens it's reasonably easy to catch the bug early during debugging/testing and even place some unit tests for it.
The opposite case would be if it's data entered by the user, or read from a file, or from a URL, anything external generally speaking. Since you cannot control what the program is dealing with: by all means, validate it as thoroughly as you can before using it in any way, as you're exposed to bogus/missing/incomplete/incorrect/malicious information that may cause problems down the path.
An intermediate case can be when the input comes from another layer/tier within the same system. It's more difficult to decide whether to do a full validation or take it for granted, since it's another piece of internal software, but might be replaced or modified independently at a later time. My preference goes towards validating again when crossing boundaries.
What to do with the validation?
Using an if (as in your sample) to simply skip over some assignment or usage may be fine for some cases. For instance, if the user is entering some data and this just shows a tooltip or other minor info, it's possibly safe to skip. But if the piece of code does something important, that in turn fills some mandatory condition or executes some other process, it's not the right approach as it will cause problems for the next code run. The thing is, when you skip over some code, it must be safe to do so, without any side effects or unwanted consequences, otherwise you would be hiding some error, and that's quite difficult to debug in later development stages.
Abort the current process gracefully is a good choice for early validations, when the failure is totally expected and you know precisely how to respond to it. An example could be a missing required field, the process gets interrupted and a message is shown to the user asking for the missing info. It's not OK to simply ignore the error, but also not serious enough to throw an exception that disrupts the normal program flow. Of course, you may still use an exception, depending on your architecture, but in any case catch it and recover gracefully.
Throw an exception is always a choice when the "impossible" really happened. It's in those cases where you cannot possibly provide a reasonable response for either continuing with some variation or cancel just the current process, it may be due to a bug or bad input somewhere, but the important thing is that you want to know it and have all the details about it, so the best possible way is to make it to blow up as loudly as possible, so that the exception bubbles up and reaches a global handler that interrupts everything, saves to a log file/DB/whatever, sends a crash report to you and finds a way to resume execution, if that's feasible or safe. At least if your app crashes, do so in the most graceful way, and leave traces for further analysis.
As always, it depends on the situation. But just using an if to avoid coding an exception handler is for sure a bad practice. It must always be there, and then some code may rely on it - whether appropriate or not - if it's not critical to fail.
I wouldn't call it defensive programming at all - I'd call it "la la la I can't hear you" programming :) Because the code appears to be effectively ignoring a potential error condition.
Obviously we don't have any idea of what comes next in your code, but since you didn't include an else clause, I can only assume that your code just carries on even in the case that x.parent is actually null.
Bear in mind that "should not possibly be null" and "is absolutely, positively guaranteed to never be null" are not necessarily the same thing; so in that case it could lead to an exception further down the line when you try to de-reference y.
The question is then - what is more acceptable within the context of the problem you are trying to solve (the "domain") and that kind of depends on what you intend to do with ylater on.
If y being null after this code is not a problem (let's say you do a defensive check later on for y!=null) then that's OK - although personally I don't like that style - you end up defensively checking every single de-reference because you can never be quite sure if you're a null reference away from crashing...
If y cannot be null after the code because it will cause an exception or missing data later on, then it's simply a bad idea to continue when you know that an invariant is not correct.
In short, I'd say this is NOT a defensive programming. I agree with those who thinks this code hides the system error instead of exposing and fixing. This code violates the 'fail fast' principle.
This is true if and only if x.parent is a mandatory non-null property (which seems to be obvious from the context.) However, if x.parent is an optional property (i.e. can reasonably have a null value) then this code can be allright depending on your business logic expressed.
I'm always considering usage of empty values (0, "", empty objects) instead of nulls which require tons of irrelevant if statements.
After some years of thinking about this issue, I use the following "defensive" programming style - 95% of my methods return string as a success / failed result.
I return string.Empty for success, and informative text string if failed. While returning the error text, I write it to log at the same time.
public string Divide(int numA, int numB, out double division)
{
division = 0;
if (numB == 0)
return Log.Write(Level.Error, "Divide - numB-[{0}] not valid.", numB);
division = numA / numB;
return string.Empty;
}
Then I use it:
private string Process(int numA, int numB)
{
double division = 0;
string result = string.Empty;
if (!string.IsNullOrEmpty(result = Divide(numA, numB, out divide))
return result;
return SendResult(division);
}
When you have Log monitoring system, it lets the system show go on, but notifies the administration.

How to know if some method can throw an exception

I'm new in a developement for Windows 8 and C#, but I have certain experience with Java Programming.
So, when I try to make some Json parser (for example) in java, I can't do it without use a try - catch block, and this way I can handle the exception, but when I try to do the same in c# (Windows 8) and I don't use the try - catch block it works too, like this:
if (json != null)
{
JObject jObject = JObject.Parse(json);
JArray jArrayUsers = (JArray)jObject["users"];
foreach (JObject obj in jArrayUsers)
{
ListViewMainViewModel user = new ListViewMainViewModel(
(String)obj["email"],
(String)obj["token"],
(String)obj["institution"],
(String)obj["uuidInstitution"]);
usersList.Add(user);
}
return usersList;
}
}
As I know the right way is to catch JsonReaderException, but Visual Studio never warned me on that. I would like to know if there's a easy way to know if some method throw an exception, like is on java using eclipse (it's mandatory implement try-catch block or code wont compile)
You will have to consult the documentation for that. C# lacks a throws keyword.
The term for what you are looking for is checked exceptions, and more info can be found in the C# FAQ.
In C# you are responsible for handling exceptions - which IMHO is the better way of going about it than the Java implementation. In effect, an exception should be, well exceptional, that is: It isn't something you should just always expect to happen.
Consider this weirding (yet, common) anti-pattern:
try {
} catch (Exception ex) { /* Handler goes here */ }
What exactly does that mean? Are you really going to handle every single exception that passes through here? Even stuff like OutOfMemoryExceptions? That's nuts. The only thing this sort of pattern will lead to is suppressing legitimate exceptions that really ought to bring down the application - this is fairly similar to the Java approach.
Think of an Exception as being a flag to the programmer that says 'hey, the environment just entered an impossible state'. For example, if I try to divide by zero and the system throws a DivideByZeroException, then rightly the system should alert you to this, because this is a failure - one the system can't just 'figure it's way out of' - and if you simply suppress the issue, how is that really helping? In the end this is counter-productive, in that all you're doing is masking over what is really an impossible application state. If you do this a lot in your application, then it eventually just devolves into a sludge of toxic wrong-ness. Yuck!
Exceptions also take up a lot of screen real estate. Sometimes I wish they would make the try/catch/finally blocks a little more streamlined, but then I remember that doing so would encourage people to use them more, so I repent of that position pretty quick.
Exceptions are useful programmer-to-programmer notifications saying that something you're doing doesn't make sense. Obviously we should never pass raw exceptions to the user because they won't know what to do with them. At the same time, you don't want to try to handle every single exception on the face of the earth, because 'handling' in this sense typically transforms into 'suppression', which is way worse than just letting the application fail (gracefully).
C#, as has been mentioned, does not have checked exceptions, and thank goodness.
The idea of checked exceptions sounds great on its face, but talk to anyone who is forced to use them by language or runtime, and they'll say there are three big problems with checked exceptions:
They impose their will upon the consuming coder. Checked exceptions, by their definition, are expected to be handled before they are thrown out of the runtime. The runtime is in effect telling the coder "you should know what to do when I throw this, so do so". First off, think about it; you are told to expect something that happens in exceptional cases by its very definition. Second, you're expected to somehow handle it. Well, that's all well and good when you actually have the ability to address the problem the exception indicates. Unfortunately, we don't always have that ability, nor do we always want to do everything we should. If I'm writing a simple form applet that performs a data transformation, and I just want my application to die a fiery death if there's any problem, I can't just not catch anything; I have to go up all possible call stacks of every method that could throw something and add what it could throw to the throws clause (or be extremely lazy and put a "throws Exception" clause on every method of my codebase). Similarly, if my app is constructed such that I can't throw out a particular exception, perhaps because I'm implementing an interface beyond my control that doesn't specify it as a potential throwable, then my only options are to swallow it entirely and return a possibly invalid result to my callers, or to wrap the exception in an unchecked throwable type like a RuntimeException and throw it out that way (ignoring the entire checked exception mechanism, which is not recommended of course).
They violate SOLID, especially the Open-Closed Principle. Make a change that adds a checked exception to your code, and if you can't handle said exception, all usages of your method must either handle it or mark themselves as throwing the exception. Usages which rethrow must be handled by their own callers or they have to be marked as throwing the same exception. By making a change as surgical as calling an alternate method in a particular line of code, you now have to trace up all possible call stacks and make other changes to code that was working just fine, just to tell them your code could conceivably throw an exception.
They create leaky abstractions by definition. A caller consuming a method with a "throws" clause must, in effect, know these implementation details about its dependency. It must then, if it is unwilling or unable to handle these errors, inform its own consumers about these errors. The problem is compounded when the method is part of an interface implementation; in order for the object to throw it, the interface must specify it as a throwable, even if not all of the implementations throw that exception.
Java mitigates this by having a multilevel hierarchy of Exception classes; all I/O-related exceptions are (supposed to be) IOExceptions, for instance, and an interface with methods that have IO-related purposes can specify that an IOException can be thrown, relieving it of the responsibility to specify each specific child IOException. This causes almost as many problems as it solves, however; there are dozens of IOExceptions, which can have very different causes and resolutions. So, you must interrogate each IOException that you catch at runtime to obtain its true type (and you get little or no help identifying the specific ones that could be thrown) in order to determine whether it's something you can handle automatically, and how.
EDIT: One more big problem:
They assume try-catch is the only way to handle a possible exception situation. Let's say you're in C# in an alternate universe where C# has Java-style checked exceptions. You want your method to open and read a file given a filename passed into it by the caller. Like a good little coder, you first validate that the file exists in a guard clause, using File.Exists (which will never throw an exception; in order to return true, the path must be valid, the file specified at the path must exist, and the executing user account must have at least read access to the folder and file). If File.Exists returns false, your method simply returns no data, and your callers know what to do (say this method opens a file containing optional config data, and if it doesn't exist, is blank or is corrupted, your program generates and uses a default configuration).
If the file exists, you then call File.Open. Well, File.Open can throw nine different types of exceptions. But none of them are likely to occur, because you already verified using File.Exists that the file can be opened read-only by the user running the program. The checked exception mechanism, however, wouldn't care; the method you're using specifies it can throw these exceptions, and therefore you must either handle them or specify that your own method can throw them, even though you may take every precaution to prevent it. The go-to answer would be to swallow them and return null (or to forget the guard clause and just catch and handle File.Open's exceptions), but that's the pattern you were trying to avoid with the guard clause in the first place.
None of this even considers the potential for evil. A developer might, for instance, catch and encapsulate an unchecked exception as a checked one (for instance, catching a NullPointerException and throwing an IOException), and now you have to catch (or specify that your method throws) an exception that isn't even a good representation of what's wrong.
As far as what to use instead in C#, the best practice is to use XML documentation comments to inform the immediate caller using your method that an exception could potentially be thrown from it. XML-doc is the .NET equivalent to JavaDoc comments, and is used in much the same way, but the syntax is different (three forward slashes followed by the comments surrounded with a system of XML tags). The tag for an exception is easy enough to specify. To efficiently document your codebase, I recommend GhostDoc. It will only generate exception comments for exceptions explicitly thrown from inside the method being documented, however, and you'll have to fill in some blanks.
I'm not a java developer, but from the answers here it seems as though the Java implementation is a burden to clients of those methods. However, C# missed an opportunity (Java-like or otherwise) to communicate to the caller the type of exceptional outcomes that could happen, as authored by the developer of the method, allowing me the caller to handle it appropriately.
Since this construct isn't built into the language, I would suggest to library developers that you adopt a wrapper class and use it as the return type for any methods that could go awry. Using said class as the return type in lieu of exceptions, clients can reason about what to expect when calling the method, as it is clearly defined in the method signature. Also, using the wrapper would allow a method to tell a client why something went awry in a way does not break the flow like exceptions do.
More on this subject here: http://enterprisecraftsmanship.com/2015/03/20/functional-c-handling-failures-input-errors/

Can I/Should I use exceptions to error check my program?

The main example here is copying a word document. I have these lines of code in my program:
try
{
File.Copy(docTemplatePath, docOutputPath, true);
}
catch (IOException e)
{
MessageBox.Show(e.ToString());
}
Now I'm trying to build in error checks. I want to make sure that the output Word Document is not open elsewhere before I try to save, because otherwise an exception is thrown.
The way I see it is that the exception is thrown to warn me of an error that is causing the default functionality of the code to not work as expected. In this sense I would feel comfortable catching an exception, reading it to discern the issue (in this case that the document is currently locked/open elsewhere) and thus showing a MessageBox to alert the user to the fact the document they're trying to write to a file that is open elsewhere.
Is this fine to do? I have seen many places over the course of my looking into this where it would seem that this is what exceptions are designed to do, and other places where people seem to think thaat using exception to do stuff like this is hideously against all programming traditions and would prefer to check themselves.
What is the overall consensus?
Thanks
You should use Exceptions to handle exceptional occurrences.
That is; sometimes there will be foreseeable circumstances: A file name entered by a user might not exist, so your code should check File.Exists() before attempting to load it, for example (not relying on an exception).
That file already being in use and locked by something else might be an exceptional situation; it probably is, so that's probably just fine.
IMO, in .Net, exceptions should be used for managed unexpected errors.
For me it's a bad idea to throw an exception for a authentification error (like bad password) but it's a good to use it for manage a database connection error.
So, in few words, i use exceptions in order to manage unexpectable issues and not business issues. The idea of doing every business issues with an exception is more an "over" object oriented approach and is not what it should be use for.
Your example is IMO a good example of the good way to use exception.
Globally it's just a "big" try/catch around functionnality or specific tasks.
AFAIK Exceptions are designed for handling things that are out of the developers control like a hardware failure or disconnected network or something similar to that, where the developer might not have the knowledge of the problem,
IMHO it is better to check for the value of divider in the expression
int r = val/divider; than to check for the DivideByZeroException
Using Exceptions to control program flow is 'not done'. They should be used only to handle exceptional circumstances, when you don't want your entire application to crash.
That said, sometime it is necessary to use Exceptions. I believe the int.TryParse and other TryParse methods in the .NET Framework use Exceptions, catch them if it doesn't work, and then return false.
If there is no other way of knowing if a Word file is already open, my opinion is that you could use an Exception to do this. The good thing is that you catch a specific exception, because other things could go wrong. The problem is that the IOException could have another source (i.e. the destination folder is not accesible, etc.). This is true not only for your example, but for all (complex) exception-driven flows. The TryParse example I gave above is fairly simple, so there, it's not so much of a problem.
Conclusion: don't do it, unless it's the only way you can. And then, try to isolate it in a separate method. This way, if you find a better solution, you can always change your implementation. Also, try to catch the most specific exception, and keep in mind that exception can have several sources.
If a routine can satisfy its contract by returning normally, it should do so. If there is no way a routine can return normally without violating its contract, it should throw an exception. If a routine's contract is taken as a given, there's really not much room for judgment in deciding whether the routine should throw an exception. It should return or throw based upon the above simple rule.
The place judgment enters into the equation is in deciding what a routine's contract should be. A useful pattern is to provide both a "Try" version of a routine and a "Do" version; if the "Try" version is unable to perform the requested action because of a reasonably-anticipated problem, it will indicate that by returning some type of error value; if a "Do" version is unable to perform the requested action, for any reason, it will throw an exception.
As a simple example, consider "Integer.TryParse" and "Integer.Parse". If one has a string which may or may not be a valid number, one may call Integer.TryParse. Integer.TryParse will use a returned flag to indicate whether the parse was successful; it will return perfectly happily whether the parse succeeded or not, and the caller is responsible for ensuring that TryParse succeeded before trying to use the returned value. By contrast, Integer.Parse will only return if the number was parsed successfully. If the number wasn't valid, Integer.Parse will throw an exception. Calling code may thus use the value returned by Integer.Parse without having to check whether it succeeded; if Integer.Parse didn't succeed, it wouldn't have returned. Note that it's possible for Integer.TryParse to throw exceptions in some truly exceptional cases (e.g. if unsafe code had made the passed-in String reference point to some other type of object); the only guarantee is that it won't throw in the reasonably-expected cases (e.g. it's passed a string like "XYZ" instead of one like "123").
A slight enhancement to the Try/Do pattern is to have a routine accept a delegate which will be invoked if something goes wrong. In many cases, passing a delegate would be overkill, and it's often hard to decide in advance what parameters the delegate should take, but this approach can be advantageous in cases where a decision of whether to muddle on or give up may be determined by outside factors. Such situations arise in communications scenarios, where a program's proper response to a communications hiccup may be to up a message notifying the user that the program is having difficulty and allow the user to hit "cancel", but to have the program retry the operation a few times if the user does not. If the operation that had to be retried was a small portion of the overall operation to be performed, throwing an exception out to the main line would 'permanently' give up on the larger operation, while performing retries without user interaction could force a user to sit annoyingly long for the computer to give up on an operation the user might know won't possibly succeed (e.g. because the battery just died on the device he was communicating with). Using a callback delegate allows the optimal user interface experience, without tying the communications code to any particular user-interface implementation.

What is Environment.FailFast?

What is Environment.FailFast?
How is it useful?
It is used to kill an application. It's a static method that will instantly kill an application without being caught by any exception blocks.
Environment.FastFail(String) can
actually be a great debugging tool.
For example, say you have an
application that is just downright
giving you some weird output. You have
no idea why. You know it's wrong, but
there are just no exceptions bubbling
to the surface to help you out. Well,
if you have access to Visual Studio
2005's Debug->Exceptions... menu item,
you can actually tell Visual Studio to
allow you to see those first chance
exceptions. If you don't have that,
however you can put
Environment.FastFail(String) in an
exception, and use deductive reasoning
and process of elimination to find out
where your problem in.
Reference
It also creates a dump and event viewer entry, which might be useful.
It's a way to immediately exit your application without throwing an exception.
Documentation is here.
Might be useful in some security or data-critical contexts.
Failfast can be used in situations where you might be endangering the user's data. Say in a database engine, when you detect a corruption of your internal data structures, the only sane course of action is to halt the process as quickly as possible, to avoid writing garbage to the database and risk corrupting it and lose the user's data. This is one possible scenario where failfast is useful.
Another use is to catch programmer errors. Say you are writing a library and some function accepts a pointer that cannot be null in any circumstance, that is, if it's null, you are clearly in presence of a programmer error. You can return an error like E_POINTER or throw some InvalidArgument exception and hope someone notices, but you'll get their attention better by failing fast :-)
Note that I'm not restricting the example to pointers, you can generalize to any parameter or condition that should never happen. Failing fast ultimately results in better quality apps, as many bugs no longer go unnoticed.
Finally, failing fast helps with capturing the state of the process as faithfully as possible (as a memory dump gets created), in particular when failing fast immediately upon detecting an unrecoverable error or a really unexpected condition.
If the process was allowed to continue, say the 'finally' clauses would run or the stack would be unwound, and things would get destroyed or disposed-of, before a memory dump is taken, then the state of the process might be altered in such as way that makes it much more difficult to diagnose the root cause of the problem.
It kills the application and even skips try/finally blocks.
From .NET Framework Design Guidelines on Exception Throwing:
✓ CONSIDER terminating the process by calling System.Environment.FailFast (.NET Framework 2.0 feature) instead of throwing an exception if your code encounters a situation where it is unsafe for further execution.
Joe Duffy discusses failing fast and the discipline to make it useful, here.
http://joeduffyblog.com/2014/10/13/if-youre-going-to-fail-do-it-fast/
Essentially, he's saying that for programming bugs - i.e. unexpected errors that are the fault of the programmer and not the programme user or other inputs or situations that can be reasonable expected to be bad - then deciding to always fail fast for unexpected errors has been seen to improve code quality.
I think since its an optional team decision and discipline, use of this API in C# is rare since in reality we're all mostly writing LoB apps for 12 people in HR or an online shop at best.
So for us, we'd maybe use this when we want deny the consumer of our API the opportunity of making any further moves.
An unhandled exception that is thrown (or rethrown) within a Task won't take effect until the Task is garbage-collected, at some perhaps-random time later.
This method lets you crash the process now -- see this answer.

Categories