문제

I have this simple piece of code:

public static int GetInt(int number)
{
    int[] ints = new int[]{ 3, 7, 9, int.MaxValue };
    foreach (int i in ints)
        if (number <= i)
            return i;

    return int.MaxValue; //this should be unreachable code since the last int is int.MaxValue and number <= int.MaxValue is allways true so the above code will allways return
}

The problem is that the compiler says that not every execution path returns a value. So I have to write code that will be never reached. My question is, what should I do in a situation like this? Should I return some default value or should I throw an exception. Also, if I want to throw an exception, what exception is suitable for throwing? I didn't find anything like UnreachableCodeException.

도움이 되었습니까?

해결책

I'd be tempted to use InvalidOperationException - or some other exception which you wouldn't explicitly catch. Give it a message which indicates that you really didn't expect to get here. This is a "world is seriously broken" failure. InvalidOperationException doesn't quite capture this, but I can't think of a better one offhand. You could always create your own exception to use throughout your codebase, of course.

Don't just return a value, as otherwise you'll never find out if your world is upside-down.

다른 팁

Use the following to show a logic failure message after your foreach:

System.Diagnostics.Debug.Fail("Unreachable code reached");

This will alert you during debugging.

In addition, also throw an exception for during production:

throw new InvalidOperationException();

Do not just return a value, especially one that is potentially valid: you'll never catch the logic error.

Rather than returning from your loop, declare a return value variable, set it, and then return once at the end of the code.

public static int GetInt(int number)
{
    var rtnVal = int.MaxValue;
    int[] ints = new int[]{ 3, 7, 9, int.MaxValue };
    foreach (int i in ints) {
        if (number <= i) {
            rtnVal = i;
            break;
        }
    }
    return rtnVal;
}

I think every case is different, but yes, ultimately you have to return something or throw an exception. The way to handle this in your code example is just to remove int.MaxValue from your array:

public static int GetInt(int number)
{
    int[] ints = new int[]{ 3, 7, 9 };
    foreach (int i in ints)
        if (number <= i)
            return i;
    return int.MaxValue;
}

Here's a LINQ option that automatically throws an exception when no match is found

public static int GetInt(int number)
{
    int[] ints = new int[]{ 3, 7, 9, int.MaxValue };
    return ints.First(i => number <= i);
}

The compiler cannot tell that your foreach loop will always return a value.

A theoretical compiler could do so since in principal the information is available, but the C# compiler cannot.

Why not just return the first value that is greater than number instead

    public static int GetInt(int number)
    {
        var ints = new[] { 3, 7, 9};
        return (ints.Any(i => i > number))? 
            ints.First(i => i > number): int.MaxValue;
    }
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top