jsrosetta

Hàm

Spread và Rest

Toán tử spread và rest của Node.js so với tham số variadic thật trong Swift và Java, slice destructuring trong Rust, và `...T` trong Go.

Phiên bản tối thiểu
Node.js ≥ 12.20Go ≥ 1.18Rust ≥ 1.58Swift ≥ 5.1Java ≥ 25
Đã chạy thử trên
Node.js 24.12.0Go 1.27.1Rust 1.98.1Swift 6.2.4Java 25.0.4.1

Code Node.js là ES module: lưu file .mjs hoặc đặt "type": "module" trong package.json.

Node.js dùng cùng một ký hiệu ... cho hai việc trái ngược nhau: "trải" một mảng thành nhiều giá trị (spread) và "gom" nhiều giá trị thành một mảng (rest). Go tách hai việc này ra: ... khi gọi hàm để trải một slice, và ...T trong khai báo tham số để gom thành slice. Swift và Java có tham số variadic thật (Int..., int...) — gần với rest của JS nhất; Java thậm chí cho phép truyền thẳng một mảng có sẵn vào tham số variadic, gần giống spread. Rust không có spread lẫn rest theo nghĩa JS: mảng cỡ cố định thì destructure qua pattern, còn "nhiều tham số" thì nhận một slice.

Spread operator

const array = [1, 2, 3, 4, 5];
 
console.log(...array); // 1 2 3 4 5

Rest operator

function sum(...nums) {
  let t = 0;
 
  for (let n of nums) {
    t += n;
  }
 
  return t;
}
 
console.log(sum(1, 2, 3, 4, 5)); // 15

Khác biệt chính

Node.js (...) Go (...) Rust Swift Java
Trải mảng thành các đối số fn(...arr) fn(slice...) (chỉ với tham số variadic) không có; destructure mảng cỡ cố định qua pattern không có; phải join thủ công mảng có sẵn truyền thẳng vào tham số variadic
Gom tham số thành mảng/slice function f(...args) func f(args ...T) nhận &[T] (không phải variadic thật) func f(_ args: T...) (variadic thật) void f(T... args) (variadic thật)
Kiểu phần tử có thể khác nhau (mixed) phải cùng kiểu T (hoặc dùng any) phải cùng kiểu T phải cùng kiểu T phải cùng kiểu T (hoặc Object...)

Tham khảo: github.com/miguelmota/golang-for-nodejs-developers#spread-operator