16

这个问题让我想起了我脑海中关于 switch 的一个老问题:

    int personType = 1;
    switch (personType)
    {
        case 1:
            Employee emp = new Employee();
            emp.ExperienceInfo();
            break;
        case 2:
            Employee emp = new Employee(); 
            //Error: A local variable named 'emp' is already defined in this scope
            emp.ManagementInfo();
            break;
        case 3:
            Student st = new Student();
            st.EducationInfo();
            break;
        default:
            MessageBox.Show("Not valid ...");
    }

为什么 emp 在“案例 2”中被识别?在 C++ 中(如果我没记错的话)我们可以同时使用多种情况,但在 C# 中这是不可能的,我们应该case 1用 break 结束,所以下面的代码在 C++ 中似乎是正确的,而在 C# 中是错误的:

case 1:
case 2:
   SomeMethodUsedByBothStates();

当我们不能有这样的行为时,为什么我们应该能够声明 emp incase 1并在其中看到它case 2?如果从来没有两种情况一起发生,那么为什么要在两者中都看到对象呢?

4

4 回答 4

34

案例不会在 c++ 或 c# 中创建范围。在 case 中声明的所有这些变量都在相同的范围内,即 switch 语句的范围内。如果您希望这些变量在某些特定情况下是本地的,则需要使用大括号:

switch (personType)
{
    case 1: {
        Employee emp = new Employee();
        emp.ExperienceInfo();
        break;
    }
    case 2: {
        Employee emp = new Employee(); 
        // No longer an error; now 'emp' is local to this case.
        emp.ManagementInfo();
        break;
    }
    case 3: {
        Student st = new Student();
        st.EducationInfo();
        break;
    }
    ...
}
于 2012-12-05T13:29:50.943 回答
5

您展示的第二个代码在 C# 中非常好,假设案例 2 有一个breakor return

case 1:
    // no code here...
case 2:
    SomeMethodUsedByBothStates();
    break;

允许空箱掉线。不允许
在 一个失败的案例分支中有代码。因此,以下内容将无效:

case 1:
    SomeMethodUsedOnlyByCase1();
    // no break here...
case 2:
    SomeMethodUsedByBothStates();
    break;

关于范围的问题是另一个问题。基本上,范围是 switch 语句本身,而不是 case 分支。

要使您的示例编译,只需通过添加花括号来为 case-branch 提供它们自己的范围:

int personType = 1;
switch (personType)
{
    case 1:
    {
        Employee emp = new Employee();
        emp.ExperienceInfo();
        break;
    }
    case 2:
    {
        Employee emp = new Employee(); 
        emp.ManagementInfo();
        break;
    }
    case 3:
    {
        Student st = new Student();
        st.EducationInfo();
        break;
    }
    default:
        MessageBox.Show("Not valid ...");
}
于 2012-12-05T13:29:23.607 回答
2

在案例中声明变量时,请使用大括号进行说明。

int personType = 1;
switch (personType)
{
    case 1: 
   {
     ///
     break;
   }
    case 2: 
   {
     ///
     break;
    }
    case 3: 
   {
        ///
        break;
   }
    ...
}
于 2012-12-05T13:35:16.473 回答
0

范围一点也不奇怪。局部变量的范围是从定义它的点到定义它的块的末尾。因此,各种emp变量都在范围内,直到以{afterswitch语句开头并在相应的}. case标签没有什么特别之处。它们不会改变变量的范围。

于 2012-12-05T14:05:06.030 回答