dart 中的位置参数和命名参数的区别?

1. 位置参数(Positional Parameters)

定义

位置参数是按 参数在函数定义中的顺序 传递的参数。调用函数时,必须按顺序传递参数,且参数名在调用时不需要指定。

分类

  • 必选位置参数:必须传递,且顺序固定。
  • 可选位置参数 :用 [] 包裹,可以不传或传部分参数。

示例

dart 复制代码
// 定义函数:两个必选参数,一个可选参数
void printInfo(String name, int age, [String? city]) {
  print('Name: $name, Age: $age');
  if (city != null) {
    print('City: $city');
  }
}

void main() {
  // 必须按顺序传递必选参数
  printInfo('Alice', 30); // 只传必选参数,可选参数不传
  printInfo('Bob', 25, 'New York'); // 传必选参数和可选参数
}

输出

yaml 复制代码
Name: Alice, Age: 30
Name: Bob, Age: 25
City: New York

关键点

  • 必选参数必须放在可选参数前面
  • 可选参数默认值 :可以在定义时设置默认值,如 int age = 18,这样不传时会用默认值。

2. 命名参数(Named Parameters)

定义

命名参数通过 参数名 传递值,调用时通过 参数名: 值 的形式指定,顺序无关,且通常是可选的。

分类

  • 可选命名参数 :用 {} 包裹,调用时可选。
  • 必选命名参数 :需用 required 标记(Dart 2.12+)。

示例

dart 复制代码
// 定义函数:两个命名参数,其中 name 是必选(required)
void printProfile({required String name, String? job, int? age}) {
  print('Name: $name');
  if (job != null) {
    print('Job: $job');
  }
  if (age != null) {
    print('Age: $age');
  }
}

void main() {
  // 必须传递必选参数 name,其他可选
  printProfile(name: 'Charlie'); // 只传必选参数
  printProfile(name: 'David', age: 30, job: 'Engineer'); // 任意顺序
  printProfile(job: 'Artist', name: 'Eve'); // 参数顺序无关
}

输出

makefile 复制代码
Name: Charlie
Name: David
Job: Engineer
Age: 30
Name: Eve
Job: Artist

关键点

  • 命名参数默认可选 ,但用 required 标记的参数必须传递。
  • 调用时必须指定参数名,顺序无关。

对比总结

特性 位置参数 命名参数
传递方式 按顺序,无需参数名 通过参数名,顺序无关
必选参数 必须按顺序传递 必须用 required 标记
可选参数 [] 包裹,顺序固定 {} 包裹,无需固定顺序
可读性 参数多时易混淆 参数多时更清晰(通过参数名)
默认值 可设置默认值 可设置默认值

使用场景

  • 位置参数 :参数少且顺序明确时(如 add(1, 2))。
  • 命名参数:参数多、可选参数多或需要清晰标识时(如 UI 组件配置)。

常见问题

Q1:为什么可选参数必须放在必选参数后面?

  • 因为 Dart 需要明确必选参数的顺序,可选参数是"补充"信息,放在最后更合理。

Q2:如何为命名参数设置默认值?

dart 复制代码
void greet({String name = 'Guest'}) {
  print('Hello, $name!');
}
greet(); // 输出:Hello, Guest!

Q3:能否同时使用位置参数和命名参数?

  • 可以,但需遵循规则:
dart 复制代码
void printDetails(String name,int? age,String? city) {
  print('Name: $name');
  if (age != null) {
    print('Age: $age');
  }
  if (city != null) {
    print('City: $city');
  }
}

代码示例(综合)

dart 复制代码
// 综合使用位置参数和命名参数
void printUser({
  required String name, // 必填参数需标记 required
  String? job, // 可选命名参数
  int? age,
  bool? isStudent,
}) {
  print('Name: $name');
  if (job != null) {
    print('Job: $job');
  }
  if (age != null) {
    print('Age: $age');
  }
  if (isStudent != null) {
    print('Is Student: $isStudent');
  }
}


void main() {

printUser(name: 'Alice'); // 输出:Name: Alice
printUser(name: 'Bob', job: 'Engineer'); // 输出:Name: Bob, Job: Engineer
printUser(
  name: 'Charlie',
  job: 'Developer',
  age: 28,
  isStudent: false,
);
}

相关推荐
竹林8189 分钟前
用 The Graph 查询链上数据实战:从手搓 RPC 到 Subgraph,我的 NFT 项目数据加载快了 10 倍
前端·javascript
妙码生花26 分钟前
从 PHP 到 AI + Golang,程序员自救转型手记(十九):点选验证码代码逐行目检
前端·后端·go
Awu12271 小时前
⚡从零开发 Agent CLI(五)实现一个可治理、可扩展的工具系统
前端·人工智能·claude
咪库咪库咪2 小时前
Vue3-生命周期
前端
莪_幻尘2 小时前
你的 AI Skill 越多越蠢?Token 上下文爆炸的求生指南
前端·ai编程
lichenyang4532 小时前
从 has.echo 到异步 API 注册表:一次 ASCF API 回调不触发的排查复盘
前端
林瞅瞅3 小时前
Nuxt3 项目部署 Nginx 防盗链后特定 JS 文件 403 问题修复方案
前端
kyriewen3 小时前
别再每次都 Google 了:我整理了前端日常最常踩的 10 个 Git 坑,附速查表
前端·javascript·git
一颗奇趣蛋3 小时前
Web 视频开发完全指南:从入门到精通
前端
非洲农业不发达4 小时前
windows终端体验大升级,让你拥有macos级别的美化
前端·后端