C#中Main方法内变量无法被其他类方法修改的原因与解决办法
问题原因与解决方案
核心原因
这和继承没有任何关系,问题出在C#的值类型传参机制上:
int属于值类型,默认传参是值传递——调用方法时会创建原变量的副本,把副本传给方法的参数。- 你代码里
ChangeVariable方法中修改的item只是test的副本,原变量test根本没被改动,所以Main方法里输出的还是初始值1。
解决办法
提供四种常用方案,按需选择:
1. 使用ref关键字(引用传递)
让方法直接操作原变量,需要在方法定义和调用时都加上ref:
TestClass stuff = new TestClass(); int test = 1; Console.WriteLine("This is an integer: {0}\nAnd this is an amount it's added with: 2", test); // 调用时加ref stuff.ChangeVariable(ref test); Console.WriteLine("\nand it's {0} here! Why doesn't the change stick!?", test); class TestClass { // 方法定义加ref public void ChangeVariable(ref int item) { item += 2; Console.WriteLine("\nFor some reason, 'item' here is {0},", item); } }
2. 使用out关键字(输出参数)
适合方法的核心目的是输出修改后的值的场景,out参数不需要提前初始化,但方法必须给它赋值:
TestClass stuff = new TestClass(); int test; // out参数无需提前初始化 Console.WriteLine("This is an integer: {0}\nAnd this is an amount it's added with: 2", test); // 调用时加out stuff.ChangeVariable(out test); Console.WriteLine("\nand it's {0} here! Why doesn't the change stick!?", test); class TestClass { // 方法定义加out public void ChangeVariable(out int item) { item = 1; // 必须先赋值 item += 2; Console.WriteLine("\nFor some reason, 'item' here is {0},", item); } }
3. 返回修改后的值,重新赋值
最直观的方案,不需要特殊关键字,通过返回值更新原变量:
TestClass stuff = new TestClass(); int test = 1; Console.WriteLine("This is an integer: {0}\nAnd this is an amount it's added with: 2", test); // 接收返回值并赋值给原变量 test = stuff.ChangeVariable(test); Console.WriteLine("\nand it's {0} here! Why doesn't the change stick!?", test); class TestClass { // 修改方法为返回int类型 public int ChangeVariable(int item) { item += 2; Console.WriteLine("\nFor some reason, 'item' here is {0},", item); return item; } }
4. 用引用类型包装值类型
把int包装到自定义类(引用类型)中,传参时传递的是对象引用的副本,修改对象的属性会影响原对象:
TestClass stuff = new TestClass(); // 使用自定义包装类 IntWrapper test = new IntWrapper { Value = 1 }; Console.WriteLine("This is an integer: {0}\nAnd this is an amount it's added with: 2", test.Value); stuff.ChangeVariable(test); Console.WriteLine("\nand it's {0} here! Why doesn't the change stick!?", test.Value); // 自定义引用类型包装类 class IntWrapper { public int Value { get; set; } } class TestClass { public void ChangeVariable(IntWrapper item) { item.Value += 2; Console.WriteLine("\nFor some reason, 'item.Value' here is {0},", item.Value); } }
额外澄清
你没有对继承存在根本性误解,这个问题完全和继承无关,本质是C#中值类型与引用类型的传参行为差异导致的。
内容的提问来源于stack exchange,提问作者SleepParalysisDemon
相关产品推荐
相关产品推荐

