Update: I'm going to leave it as is: The performance hit of a exception (very rare) is better than the probably performance hit for checking on each operation (common)
I'm trying to support an "EstimatedRowCount" that in one case would be the product of two sub-cursors that are joined together:
estimatedRowCount = left.EstimatedRowCount * right.EstimatedRowCount;
return estimatedRowCount;
Of course, if left and right are big enough, this will throw an OverflowException.
Here, I don't really care if estimatedRowCount is 100% accurate, just big enough to know that this cursor is holding a lot of data.
Right now, I'm doing this:
// We multiply our rowcount
Int64 estimRowCount = 0;
try
{
estimRowCount = leftRowCount * rightRowCount;
}
catch (OverflowException)
{
// Ignore overflow exceptions
estimRowCount = Int64.MaxValue;
}
return estimRowCount;
Is there a better way to test for overflow operations so I don't have to do the try{}catch to guard?
This sounds like a good use case for the 'unchecked' keyword.
To use, simply wrap your assignment in an 'unchecked' block:
Int64 estimRowCount = 0;
unchecked
{
estimRowCount = leftRowCount * rightRowCount;
}
Then test to see if the result is negative - if it is, it overflowed:
if (estimRowCount > 0) estimRowCount = Int64.MaxValue;
You'll need to ensure in this case that neither leftRowCount nor rightRowCount can be negative, but given the context I don't think that'll occur.
if (Int64.MaxValue / leftRowCount <= rightRowCount)
{
estimRowCount = leftRowCount * rightRowCount
}
else
{
estimRowCount = Int64.MaxValue;
}
Not sure if I could explain myself without an editor.
But, I hope you get the idea.
Your solution seems quite reasonable. Is there something specific you want to optimize? Does that product cause the overflow condition so frequently that you're worried about the performance hit of the exception handling?
(Just simple food for thought, if leftRowCount and rightRowCount are Int32, not Int64, then your product cannot overflow your Int64 estimRowCount lvalue.)
Related
I just came across this keyword for the first time. What does it do, and when should it be used?
int multiply(int i, int j)
{
return checked(i * j);
}
Eric Lippert has a two-part blog post "What is the unchecked keyword good for?": Part 1 -- Part 2
"Checked" is a block keyword that enables arithmetic overflow checking. Normally, if an integer operation exceeds the maximum or minimum value that the type can handle, the operation proceeds anyway, and the result just cycles like an odometer. So, for example:
byte b = byte.MaxValue;
Console.WriteLine(b); // 255 (11111111)
Console.WriteLine(++b); // 0 (00000000)
Placing this snippet in a checked block prevents the overflow, and instead the runtime throws an OverflowException:
checked
{
byte b = byte.MaxValue;
Console.WriteLine(b); // b=255
try
{
Console.WriteLine(++b);
}
catch (OverflowException e)
{
Console.WriteLine(e.Message); // "Arithmetic operation resulted in an overflow."
// b = 255
}
}
And since there's a compiler option /checked, which turns compiler checking on by default, there is also the unchecked keyword which prevents overflow checking.
As far as usage, overflow checking should be used sparingly, as is true of exception handling in general. To check for an overflow at runtime, it's significantly faster (like, an order of magnitude) to do a simple check, rather than to turn on overflow checking:
int multiply(int i, int j)
{
if ((long)i * (long)j > int.MaxValue)
throw new InvalidOperationException("overflow");
return i*j;
}
You can do this even for Int64/long, using BigInteger (this can be still at least an order of magnitude faster than using checked):
long multiply(long i, long j)
{
if (new System.Numerics.BigInteger(i) + j > long.MaxValue)
throw new InvalidOperationException("overflow");
return i*j;
}
There's also a good Code Project article on this that explains some caveats (eg, the overflow check only applies to the immediate code block, not to any function calls inside the block).
I just came across this keyword for the first time. What does it do, and when should it be used?
int multiply(int i, int j)
{
return checked(i * j);
}
Eric Lippert has a two-part blog post "What is the unchecked keyword good for?": Part 1 -- Part 2
"Checked" is a block keyword that enables arithmetic overflow checking. Normally, if an integer operation exceeds the maximum or minimum value that the type can handle, the operation proceeds anyway, and the result just cycles like an odometer. So, for example:
byte b = byte.MaxValue;
Console.WriteLine(b); // 255 (11111111)
Console.WriteLine(++b); // 0 (00000000)
Placing this snippet in a checked block prevents the overflow, and instead the runtime throws an OverflowException:
checked
{
byte b = byte.MaxValue;
Console.WriteLine(b); // b=255
try
{
Console.WriteLine(++b);
}
catch (OverflowException e)
{
Console.WriteLine(e.Message); // "Arithmetic operation resulted in an overflow."
// b = 255
}
}
And since there's a compiler option /checked, which turns compiler checking on by default, there is also the unchecked keyword which prevents overflow checking.
As far as usage, overflow checking should be used sparingly, as is true of exception handling in general. To check for an overflow at runtime, it's significantly faster (like, an order of magnitude) to do a simple check, rather than to turn on overflow checking:
int multiply(int i, int j)
{
if ((long)i * (long)j > int.MaxValue)
throw new InvalidOperationException("overflow");
return i*j;
}
You can do this even for Int64/long, using BigInteger (this can be still at least an order of magnitude faster than using checked):
long multiply(long i, long j)
{
if (new System.Numerics.BigInteger(i) + j > long.MaxValue)
throw new InvalidOperationException("overflow");
return i*j;
}
There's also a good Code Project article on this that explains some caveats (eg, the overflow check only applies to the immediate code block, not to any function calls inside the block).
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 9 years ago.
Improve this question
In C#, sometimes there are code paths that don't return a value, and it is nice that the compiler errors out, and allows you to fix them. However there are times where there STRUCTURALLY is a place where it doesn't, but the ALOGIRTHM would prevent that structure from happening.
Here is a simple contrived example.
public static int test1(bool a)
{
if (a) return 1;
if (!a) return 2;
}
Of course people will tell me , that my "algorithm" is stupid and my second test is redundant and I should just do.
public static int test1(bool a)
{
if (a) return 1;
else return 2;
}
or even
public static int test1(bool a)
{
if (a) return 1;
return 2;
}
I purposely choose this simple "Redundant" example, rather than my real world algorithms, as I want to focus on this issue specifically, not about 10 different ways I could have written the algorithm :)
So what are the possible ways to deal with this, and what are the pro's and con's of each.
1) is what we just covered, and that's refactor the algorithm. Sometimes this may not be possible, or the end result may not be as per formant, easy to read/understand or maintain.
other is just to return something that would never happen, such as null.. but in this case i'm dealing with an integer and i'd have to put 0, which feels ever dirtier
public static int test1(bool a)
{
if (a) return 1;
if (!a) return 2;
//this code never happens, but i need to keep the compiler happy
return 0;
}
or use exceptions
public static int test1(bool a)
{
if (a) return 1;
if (!a) return 2;
throw new Exception("this code never happens, but i need to keep the compiler happy");
}
however every time I've dealt with this , no matter what technique I take i'm not happy with the result and feel a little dirty.
Are there alternatives?
Generally you throw Exceptions when there is an exceptional case... a bool not being true or false would be rather exceptional! I would throw an exception to keep the compiler happy, but also because you don't know how the method could change in the future.
I wouldn't consider an if ... else as dirty when dealing with a bool for exactly the reason that you use bools, they only have two values, when there are more possibilities (i.e. a string) then you can use more complex test.
When you have a compile error that all your code paths do not return a value, there is no flag to set or "trick," you have to either return a default value or throw an exception. I'm a firm believer in throwing an InvalidOperationException("Unexpected code reached, this method has been modified incorrectly").
Why it's not dirty: if someone else comes along and makes a change that causes your exception to be thrown, they'll know they did something that the author of the exception viewed as fundamentally wrong. Returning a default value could quietly break the consumers of the method, so it's good practice to use an exception as a safety net.
public static int test1(bool a)
{
return a ? 1 : 2;
}
Use a variable and assign the value to it and then return that value at the end of the function.
private bool isValid()
{
bool result = false;
try {
//some code
result = true;
} catch {
result = false;
}
return result;
}
Another option you might consider in this case is using the Debug.Fail() method.
public static int test1()
{
if (myComplexAlgo()) return 1;
if (myCatchAllAlgo()) return 2;
Debug.Fail("I should never be here!");
return -1;
}
It isn't a good fit for everyone, the advantage in this method is that you can use it to make sure your tests fail without possibly crashing your production code. This can (hopefully) catch future problems in the code in case your algorithm or conditions change.
Often I find myself having a expression where a division by int is a part of a large formula. I will give you a simple example that illustrate this problem:
int a = 2;
int b = 4;
int c = 5;
int d = a * (b / c);
In this case, d equals 0 as expected, but I would like this to be 1 since 4/5 multiplied by 2 is 1 3/5 and when converted to int get's "rounded" to 1. So I find myself having to cast c to double, and then since that makes the expression a double also, casting the entire expression to int. This code looks like this:
int a = 2;
int b = 4;
int c = 5;
int d = (int)(a * (b / (double)c));
In this small example it's not that bad, but in a big formula this get's quite messy.
Also, I guess that casting will take a (small) hit on performance.
So my question is basically if there is any better approach to this than casting both divisor and result.
I know that in this example, changing a*(b/c) to (a*b)/c would solve the problem, but in larger real-life scenarios, making this change will not be possible.
EDIT (added a case from an existing program):
In this case I'm caclulating the position of a scrollbar according to the size of the scrollbar, and the size of it's container. So if there is double the elements to fit on the page, the scrollbar will be half the height of the container, and if we have scrolled through half of the elements possible, that means that the scroller position should be moved 1/4 down so it will reside in the middle of the container. The calculations work as they should, and it displays fine. I just don't like how the expression looks in my code.
The important parts of the code is put and appended here:
int scrollerheight = (menusize.Height * menusize.Height) / originalheight;
int maxofset = originalheight - menusize.Height;
int scrollerposition = (int)((menusize.Height - scrollerheight) * (_overlayofset / (double)maxofset));
originalheight here is the height of all elements, so in the case described above, this will be the double of menusize.Height.
Disclaimer: I typed all this out, and then I thought, Should I even post this? I mean, it's a pretty bad idea and therefore doesn't really help the OP... In the end I figured, hey, I already typed it all out; I might as well go ahead and click "Post Your Answer." Even though it's a "bad" idea, it's kind of interesting (to me, anyway). So maybe you'll benefit in some strange way by reading it.
For some reason I have a suspicion the above disclaimer's not going to protect me from downvotes, though...
Here's a totally crazy idea.
I would actually not recommend putting this into any sort of production environment, at all, because I literally thought of it just now, which means I haven't really thought it through completely, and I'm sure there are about a billion problems with it. It's just an idea.
But the basic concept is to create a type that can be used for arithmetic expressions, internally using a double for every term in the expression, only to be evaluated as the desired type (in this case: int) at the end.
You'd start with a type like this:
// Probably you'd make this implement IEquatable<Term>, IEquatable<double>, etc.
// Probably you'd also give it a more descriptive, less ambiguous name.
// Probably you also just flat-out wouldn't use it at all.
struct Term
{
readonly double _value;
internal Term(double value)
{
_value = value;
}
public override bool Equals(object obj)
{
// You would want to override this, of course...
}
public override int GetHashCode()
{
// ...as well as this...
return _value.GetHashCode();
}
public override string ToString()
{
// ...as well as this.
return _value.ToString();
}
}
Then you'd define implicit conversions to/from double and the type(s) you want to support (again: int). Like this:
public static implicit operator Term(int x)
{
return new Term((double)x);
}
public static implicit operator int(Term x)
{
return (int)x._value;
}
// ...and so on.
Next, define the operations themselves: Plus, Minus, etc. In the case of your example code, we'd need Times (for *) and DividedBy (for /):
public Term Times(Term multiplier)
{
// This would work because you would've defined an implicit conversion
// from double to Term.
return _value * multiplier._value;
}
public Term DividedBy(Term divisor)
{
// Same as above.
return _value / divisor._value;
}
Lastly, write a static helper class to enable you to perform Term-based operations on whatever types you want to work with (probably just int for starters):
public static class TermHelper
{
public static Term Times(this int number, Term multiplier)
{
return ((Term)number).Times(multiplier);
}
public static Term DividedBy(this int number, Term divisor)
{
return ((Term)number).DividedBy(divisor);
}
}
What would all of this buy you? Practically nothing! But it would clean up your expressions, hiding away all those unsightly explicit casts, making your code significantly more attractive and considerably more impossible to debug. (Once again, this is not an endorsement, just a crazy-ass idea.)
So instead of this:
int d = (int)(a * (b / (double)c)); // Output: 2
You'd have this:
int d = a.Times(b.DividedBy(c)); // Output: 2
Is it worth it?
Well, if having to write casting operations were the worst thing in the world, like, even worse than relying on code that's too clever for its own good, then maybe a solution like this would be worth pursuing.
Since the above is clearly not true... the answer is a pretty emphatic NO. But I just thought I'd share this idea anyway, to show that such a thing is (maybe) possible.
First of all, C# truncates the result of int division, and when casting to int. There's no rounding.
There's no way to do b / c first without any conversions.
Multiply b times 100. Then divide by 100 at the end.
In this case, I would suggest Using double instead, because you don't need 'exact' precision.
However, if you really feel you want to do it all without floating-point operation, I would suggest creating some kind of fraction class, which is far more complex and less efficient but you can keep track of all dividend and divisor and then calculate it all at once.
Handling integer overflow is a common task, but what's the best way to handle it in C#? Is there some syntactic sugar to make it simpler than with other languages? Or is this really the best way?
int x = foo();
int test = x * common;
if(test / common != x)
Console.WriteLine("oh noes!");
else
Console.WriteLine("safe!");
I haven't needed to use this often, but you can use the checked keyword:
int x = foo();
int test = checked(x * common);
Will result in a runtime exception if overflows. From MSDN:
In a checked context, if an expression produces a value that is
outside the range of the destination type, the result depends on
whether the expression is constant or non-constant. Constant
expressions cause compile time errors, while non-constant expressions
are evaluated at run time and raise exceptions.
I should also point out that there is another C# keyword, unchecked, which of course does the opposite of checked and ignores overflows. You might wonder when you'd ever use unchecked since it appears to be the default behavior. Well, there is a C# compiler option that defines how expressions outside of checked and unchecked are handled: /checked. You can set it under the advanced build settings of your project.
If you have a lot of expressions that need to be checked, the simplest thing to do would actually be to set the /checked build option. Then any expression that overflows, unless wrapped in unchecked, would result in a runtime exception.
Try the following
int x = foo();
try {
int test = checked (x * common);
Console.WriteLine("safe!");
} catch (OverflowException) {
Console.WriteLine("oh noes!");
}
The best way is as Micheal Said - use Checked keyword.
This can be done as :
int x = int.MaxValue;
try
{
checked
{
int test = x * 2;
Console.WriteLine("No Overflow!");
}
}
catch (OverflowException ex)
{
Console.WriteLine("Overflow Exception caught as: " + ex.ToString());
}
Sometimes, the simplest way is the best way. I can't think a better way to write what you wrote, but you can short it to:
int x = foo();
if ((x * common) / common != x)
Console.WriteLine("oh noes!");
else
Console.WriteLine("safe!");
Note that I didn't remove the x variable because it'd be foolish to call the foo() three times.
Old thread, but I just ran into this. I didn't want to use exceptions. What I ended up with was:
long a = (long)b * (long)c;
if(a>int.MaxValue || a<int.MinValue)
do whatever you want with the overflow
return((int)a);
So, I ran into this far after the fact, and it mostly answered my question, but for my particular case (in the event anyone else has the same requirements), I wanted anything that would overflow the positive value of a signed int to just settle at int.MaxValue:
int x = int.MaxValue - 3;
int someval = foo();
try
{
x += someval;
}
catch (OverflowException)
{
x = int.MaxValue;
}