在JavaScript中互换变量的4种方法

1,012 阅读5分钟

很多算法都需要交换2个变量。

在编码面试中,你可能会被问到*"如何在没有临时变量的情况下交换2个变量?"。*

了解执行变量交换的多种方法是很好的。在这篇文章中,你将读到4种交换的方法(2种使用额外的内存,2种不使用)。

1.解构赋值

解构赋值(ES2015的一个特性)让你可以将数组中的项目提取到变量中。例如,下面的代码是对一个数组进行析构。

let a;
let b;
[a, b] = [1, 2, 3];
a; // => 1
b; // => 2

知道了如何解构数组,就很容易用它来交换变量了。让我们用结构化赋值来交换变量ab

javascript

let a = 1;
let b = 2;
[a, b] = [b, a];
a; // => 2
b; // => 1

在第一步,在析构的右侧,创建了一个临时数组 [b, a] (其值为[2, 1] )。

然后对临时数组进行解构:[a, b] = [2, 1] 。变量a 被分配给2b 被分配给1ab 的互换已经完成。

我喜欢去结构化的方法,因为它简短而富有表现力:只用一条语句就能完成交换。它适用于任何数据类型:数字、字符串、布尔运算、对象。

我建议在大多数情况下使用结构化赋值来交换变量。

2.临时变量

使用临时变量来交换变量是很经典的。顾名思义,这种方法需要一个额外的临时变量。

让我们使用一个临时变量ab 来交换变量的值,temp

javascript

let a = 1;
let b = 2;
let temp;
temp = a;
a = b;
b = temp;
a; // => 2
b; // => 1

temp临时变量

在第一步,temp 被分配到a 的值。然后a 变量被分配到b 的值。最后,变量b 被分配到temp 的值(初始值为a )。

使用临时变量交换变量的方法适用于任何数值类型,如数字、字符串、布尔、对象。

这种方法的缺点是需要一个专门的临时变量,加上交换发生在3条语句中。

3.加法和差分

你可以不使用额外的内存(如临时数组或变量)来交换变量。

下面的例子使用加法+ 和差法- 算术运算符交换了变量ab

javascript

let a = 1;
let b = 2;
a = a + b;
b = a - b;
a = a - b;
a; // => 2
b; // => 1

最初,a1b2 。让我们看看这3个语句是如何进行互换的。

  1. a = a + b 分配给 的值是 。a 1 + 2
  2. b = a - b 给 赋值为 ( 现在是 )。b 1 + 2 - 2 = 1``b 1
  3. a = a - b 给 赋值 ( 现在是 )。a 1 + 2 - 1 = 2``a 2

最后,a2b1ab 的互换已经完成。

虽然这种方法不使用临时变量,但它有相当大的限制。

首先,你只能调换整数。其次,在第一步a = a + b 进行加法时要注意数字的溢出(总和必须低于Number.MAX_SAFE_INTEGER )。

4.位数XOR运算法则

如果操作数不同,XOR运算符的评估结果为真。作为提醒,这里是XOR真值表。

┌─────┬─────┬───────┐
│ aba ^ b │
├─────┼─────┼───────┤
│ 000   │
│ 110   │
│ 011   │
│ 101   │
└─────┴─────┴───────┘

在JavaScript中,位数XOR运算符n1 ^ n2n1n2 的每一位数字进行XOR运算。

例如,这里是5 ^ 7 如何评估为2

1 0 1 (5 in binary)
1 1 1 (7 in binary)
-----
0 1 0 (5 ^ 7 = 2 in binary)

位向XOR有两个有趣:

  • n ^ n = 0:在同一个数字上进行的位向XOR是0
  • n ^ 0 = n:在一个数字和零上进行的位数XOR是同一个数字

这些XOR属性可以用来交换变量。让我们看看如何交换ab 变量。

javascript

let a = 1;
let b = 2;
a = a ^ b;
b = a ^ b;
a = a ^ b;
a; // => 2
b; // => 1

这里解释一下为什么互换会成功:

  1. a = a ^ b
  2. b = a ^ b.基于1a 被替换成a ^ b 。因此,b = (a ^ b) ^ b = a ^ (b ^ b) = a ^ 0 = a.记住比b 现在是a.
  3. a = a ^ b.基于1a 被替换为a ^ b ,基于2b 被替换为a 。因此,a = (a ^ b) ^ a = b ^ (a ^ a) = b ^ 0 = b 。变量a 变成b

如果你觉得这个解释很复杂,可以跳过它。位数XOR(n ^ n = 0n ^ 0 = n)的属性由3个赋值组成,可以让你交换ab 的值。

使用位数XOR运算法则交换变量有局限性:你只能交换整数。

5.总结

JavaScript提供了许多交换变量的好方法,包括使用或不使用额外的内存。

第一种方法,我推荐用于日常使用,是通过应用结构化赋值来交换变量[a, b] = [b, a] 。这是一种简短而富有表现力的方法。

第二种方法是使用一个临时变量。这是对结构化赋值方法的一个很好的替代。

第三种方法,使用加法和减法,不使用额外的变量或内存。然而,该方法只限于交换整数。

以同样的方式,第四种使用位数XOR的方法也不使用额外的内存。但同样,你只能交换整数。

你喜欢用什么方法来交换变量?