Using the Checked and Unchecked keywords in C# to perform overflow checking
Overview
In C#, the Integer type is used a lot to store values within methods. Often we do not think about the limits that the Integer has. By default, the maximum value it can hold is 2147483647. If we try to cram more into an Integer we receive an overflow error as the range has been met.
The Checked keyword is a way to see if integer arithmetic, including casts, can hold a value and if not it will generate a System.OverflowException error that can be handled elegantly. This keyword has been around since Visual Studio 2003 but little has been written on it. This article will examine how to use the Checked and Unchecked keywords.
Constant Values
Only constant values will cause the checked expression to fail. If the value is not a constant then it will not raise an overflow exception.
For example, the following line:
int x = 2147483647 + 1;
will generate an error message stating “The operation overflows at compile time in checked mode”.
However, doing any work with non-constant values will not display an error. In this line we will use a variable to add 1 to the maximum integer value:
int y = 1;
int x = 2147483647 + y;
Console.WriteLine(x);
This expression will not raise an error message. Instead, it will sum the value of two positive integers and produce a negative result: -2147483648.
Checked Keyword
You can do overflow checking with compiler options or with the Checked keyword on an expression or method.
To use the compiler option, you can set the /checked option on the Build tab of the project’s properties to check for integer overflows which will cause an exception at run time. This will check all of your code automatically but at a cost as it might slow down your program to do so. For more information about this option, see /checked (C# Compiler Options).
For expression checking, wrap the statement you wish to validate in the checked value:
int x = checked(2147483647 + 1);
You can also check blocks of code encapsulated in braces:
checked {
int y = 1;
int x = 2147483647 + y;
Console.WriteLine(x);
}
The keyword will only validate the code inside the braces. If your code calls other methods they will not be verified by the Checked keyword.
Both examples above raise an overflow exception. Following best practices, wrap these values in a try-catch block so as to handle the raised exception:
using System;
public class Program
{
static int maxIntValue = 2147483647;
public static void Main()
{
Console.WriteLine(CheckedMethod());
}
static int CheckedMethod()
{
int x = 0;
try
{
x = checked (maxIntValue + 1);
}
catch (System.OverflowException e)
{
Console.WriteLine("Overflow exception due to unchecked integer value: " + e.ToString());
}
return x;
}
}
The code above will generate the following error: Overflow exception due to unchecked integer value: System.OverflowException: Arithmetic operation resulted in an overflow.
Unchecked
C# also has the Unchecked keyword. This will allow you prevent overflow checking on certain items. It can be applied to expressions within a Checked method or to entire blocks of code if you have enabled the compiler option. This keyword is useful if want to label multiple items as Checked with a single line as Unchecked.
Conclusion
The Checked/Unchecked keywords are useful for trapping arithmetic overflows of integer values. It provides a way to elegantly trap for these occurrences and to handle the errors gracefully.
Some best practices to observe when using the keywords are:
- Only use the Checked/Unchecked keywords when an overflow is possible.
- Do not turn on the Compiler option in Release mode.
- Checked will not prevent a DivideByZeroException when a divide by zero is attempted.