【问题标题】:Is it possible to define a public variable in a private method?是否可以在私有方法中定义公共变量?
【发布时间】:2016-08-29 16:57:38
【问题描述】:

我有一个有 2 个私有方法的类。在方法 A 中,我定义了一个变量,比如 varA 计数。在方法 B 中,需要再次使用 varA。

然而,varA 就像临时计数器一样,似乎不应该被视为类的属性。

那么如何在私有方法 B 中访问 varA?是否可以在私有方法 A 中将 varA 定义为 public?

public class MyClass{

  private void methodA(){
     private int varA;
     varA = GetSingleValesFromDB();
     .......
  }
  private void methodB(){
    //here, I need to access varA again
    //but I don't want to define varA as attribute of MyClass
  }

}

编辑:
课程背景:
实际上方法A和方法B可以独立运行。但就在这一次我运行方法 A 然后方法 B。我必须使用 GetSingleValesFromDB() 在方法 B 中再次获取值,就像我在方法 A 中所做的那样。
但是,即使方法 A 和方法 B 的执行之间存在时间间隔,从 DB 获取的值也不会改变,所以我不想在方法 B 中再次运行 GetSingleValesFromDB() ,这会消耗 DB 和连接资源。相反,我更喜欢重用 varA 的值。

【问题讨论】:

  • 请在这里分享您的代码
  • 任何方法,无论其保护级别如何,都不会以合理的方式公开其任何 本地 变量,从而为其赋予保护级别。跨度>
  • 为什么不应该在方法之外定义?如果您在方法内声明变量,则范围将在方法内。
  • 您不会在方法中声明公共或私有任何内容,您只声明局部变量。您可以在外部声明变量,但是可以将其设为公共或私有。
  • 您编辑的代码没有编译。正如我所说,局部变量没有保护级别,所以private int varA; 中的methodA 是一个错误。而不是这个破碎的提议,也许更详细地充实你想要解决的问题,以及为什么你认为共享局部变量是解决方案的一部分。

标签: c# private public access-modifiers


【解决方案1】:

首先,您提供的示例代码不会编译,因为在方法中声明的变量自动是本地的 - 也就是说,它始终是该方法私有的。因此,添加公共/私人访问修饰符是无效的。我还假设有一些其他方法(“methodC”)调用methodAmethodB(因为它们都是私有的),所以你的起始代码应该是这样的:

public class MyClass{

  private void methodA(){
    int varA;
    varA = GetSingleValesFromDB();
    .......
  }

  private void methodB(){
    DoSomething(varA);
    .......
  }

  public void methodC(){
    methodA();
    methodB();
  }
}

您有几种方法可以在methodAmethodB 之间共享varA 的值:

  • 两次检索值

最简单的选择是在每个方法中重新声明和检索varA,这样您就有两个不同的局部变量,因此:

public class MyClass{

  private void methodA(){
    int varA;
    varA = GetSingleValesFromDB();
    .......
  }

  private void methodB(){
    int varA;
    varA = GetSingleValesFromDB();
    DoSomething(varA);
    .......
  }

  public void methodC(){
    methodA();
    methodB();
  }
}

如果GetSingleValesFromDB 是一个廉价的调用,并且不会在运行methodAmethodB 之间切换,那么这是一种安全且简单的方法;但是,鉴于您的问题(以及对数据库的隐含调用),我认为这不能满足您的需求。

  • 共享变量和值

您可以将变量从方法本地提升为私有类成员,这使得它(以及它的值)可用于所有方法:

public class MyClass{

  private int varA;

  private void methodA(){
     varA = GetSingleValesFromDB();
     .......
  }

  private void methodB(){
    DoSomething(varA);
    .......
  }

  public void methodC(){
    methodA();
    methodB();
  }
}

但是,如果此值可能会从一次执行 methodA/methodB 更改为下一次执行,则将变量设为类成员会产生错误的印象 - 暗示(正如您在问题中所建议的那样)它是类的属性,当它实际上是与方法执行相关的状态时。

  • 传递状态对象

将共享状态包装在一个小数据对象中并将其传递给两个方法:

public class MyClass{

  private class MyMethodState
  {
    public int varA;
  }

  private void methodA(MyMethodState state){
    state.varA = GetSingleValesFromDB();
    .......
  }

  private void methodB(MyMethodState state){
    DoSomething(state.varA);
    .......
  }

  public void methodC(){
    var state = new MyMethodState();
    methodA(state);
    methodB(state);
  }
}

methodA 中提供的varA 的值将在方法调用之间传递,并在整个方法执行(这里由methodC 表示)完成时进行整理。 我认为这最接近您正在寻找的内容,因为它在方法之间保持varA 的值并清楚地确定您存储的值是什么,以及它在程序执行中“存在”多长时间。如果 MyMethodState 变得太大,您可能希望将其扩展为具有自己的方法的完整类,但对于这些简单的调用,纯数据对象应该可以满足您的需求。

【讨论】:

    【解决方案2】:

    如果你在一个方法中声明变量,那么你不能从另一个方法访问它,你可以这样实现

    public class MyClass
        {
    
            private int MethodA()
            {
                int varA = GetSingleValesFromDB()
                // do other this using varA
                // then return
                return varA;
            }
    
            private void MethodB()
            {
               int varB = MethodA(); // this case varA will assign to varB
               // then use varB for anything
            }
        }
    

    【讨论】:

      【解决方案3】:

      如果您不想生成成员,您可以生成包含所需对象的字典。

      public class MyClass
      {
          private IDictionary<string, object> session = new Dictionary<string, object>();
      
          private void methodA()
          {
              session["varA"] = GetSingleValesFromDB();
          }
      
          private void methodB()
          {
              var varA = session["varA"];
          }
      }
      

      【讨论】:

        【解决方案4】:

        你不能。

        唯一的方法是让它在课堂上,你说你不想这样做。

        我不确定这是什么原因?您是否考虑过在类上创建一个私有变量,以便只有该类的成员才能访问它?

        【讨论】:

          猜你喜欢
          • 2018-11-12
          • 2014-01-02
          • 2012-10-09
          • 1970-01-01
          • 2014-10-06
          • 2013-05-03
          • 2013-07-27
          • 1970-01-01
          • 2011-05-25
          相关资源
          最近更新 更多