You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Dart中List与int的传递机制疑问:是否分别为按引用传递与按值传递?

关于Dart中List和int的参数传递问题拆解

嘿,这个问题刚好戳中了很多刚接触Dart的开发者容易混淆的点——先直接给你澄清:Dart里所有参数传递都是按值传递,但因为不同数据类型的特性,看起来像是有“按引用传递”和“按值传递”的区别,咱们结合你的代码一步步说清楚。

先看List的例子

你的代码片段:

void main() { 
  var foo = ['a','b']; 
  var bar = foo; 
  bar.add('c'); 
  print(foo); // [a, b, c] 
  print(bar); // [a, b, c] 
}

这里的逻辑是:

  • foo 是一个引用变量,它存储的不是整个List的内容,而是这个List对象在内存中的地址。
  • 当你执行 var bar = foo 时,其实是把foo里存储的那个地址值复制了一份给bar。现在foo和bar都指向同一个List对象。
  • 所以用bar.add('c')修改的是这个共享的List对象的内部状态,自然foo也能看到变化。这不是“按引用传递”,而是传递的是引用的值,两个变量共享同一个对象实例而已。

再看int的例子

对应的代码:

var a = 3; 
int b = a; 
b += 2; 
print(a); // 3 
print(b); // 5

这里的核心是:

  • int 是Dart中的不可变值类型,变量a直接存储的就是数值3,而不是某个对象的地址。
  • 当你执行int b = a时,是把a里的数值3完整复制了一份给b,此时a和b是完全独立的两个变量,各自存储3。
  • 之后b += 2的操作,其实是创建了一个新的int对象(值为5),然后让b指向这个新对象,而a仍然指向原来的3,所以两者互不影响。

哪些类型会有类似“引用”或“值”的表现?

  • 类似“引用传递”效果的类型:所有可变的对象类型,比如List、Map、自定义的类实例等。这类变量存储的是对象的引用,赋值或传参时复制的是引用值,多个变量指向同一个对象,修改对象内部状态会影响所有指向它的变量。
  • 类似“值传递”效果的类型:所有不可变的值类型,比如int、double、String、bool、num等。这类变量直接存储值本身,赋值时复制整个值,修改其中一个不会影响另一个。(比如String也是不可变的,你执行var s1 = 'hi'; var s2 = s1; s2 += ' there';,s1还是'hi',s2会变成'hi there'——因为s2指向了新创建的字符串对象)

一个关键误区纠正

很多人会把“传递引用的值”和真正的“按引用传递”搞混。真正的按引用传递允许你修改传入变量的指向,但Dart做不到这点。比如下面的例子:

void changeList(List<String> list) {
  // 让函数内的list变量指向一个全新的List对象
  list = ['x', 'y']; 
}

void main() {
  var myList = ['a', 'b'];
  changeList(myList);
  print(myList); // 输出还是['a','b']
}

如果Dart是按引用传递,外部的myList应该会变成['x','y'],但实际并没有——因为函数内的list是外部myList的引用值的副本,修改它的指向不会影响外部变量。这就彻底证明了Dart是按值传递的。

内容的提问来源于stack exchange,提问作者fendy3d

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.29 03:37:31