给定一个可包含重复数字的序列 nums
,按任意顺序 返回所有不重复的全排列。
示例 1:
输入:nums = [1,1,2]
输出:
[[1,1,2],
[1,2,1],
[2,1,1]]
示例 2:
输入:nums = [1,2,3]
输出:[[1,2,3],[1,3,2],[2,1,3],[2,3,1],[3,1,2],[3,2,1]]
使用 全排列 函数生成所有排列,然后去重以得到最终结果
/**
* @param {number[]} nums
* @return {number[][]}
*/
var permuteUnique = function(nums) {
const result = [];
if (nums.length === 1) {
return [nums];
} else { //遍历每一项
for (let i = 0; i < nums.length; i++) {
let first = nums[i]; //拿到当前的元素
let left = nums.slice(0, i).concat(nums.slice(i + 1)); //除当前元素的其他元素组合
let rest = permuteUnique(left); //上一次递归返回的全排列
for (let j = 0; j < rest.length; j++) { //组合在一起
let next = [first].concat(rest[j]);
result.push(next);
}
}
}
// 将数组中的每个排列转换为字符串形式
const stringArr = result.map(arr => arr.join(','));
// 使用 Set 进行去重
const uniqueSet = new Set(stringArr);
// 先将 Set 转换为数组,然后使用 map 函数将字符串数组转换回数字数组
const uniqueArr = Array.from(uniqueSet, str => str.split(',').map(Number));
return uniqueArr;
};
Array.from()
是 JavaScript 中的一个静态方法,它用于从类数组或可迭代对象创建一个新的数组实例。这个方法非常有用,因为它提供了一种简便的方式来将各种集合或看起来像数组的对象转换成真正的数组。
const arrayLike = {
'0': 'a',
'1': 'b',
'2': 'c',
length: 3
};
const actualArray = Array.from(arrayLike);
// actualArray 将会是 ['a', 'b', 'c']
在上面的例子中,arrayLike
是一个类似于数组的对象,它具有索引属性和 length
属性。使用 Array.from()
可以创建一个新的数组,其中包含了 arrayLike
中的元素。
Array.from()
还可以接受一个映射函数作为第二个参数,这个函数会在创建新数组的过程中被调用,用于转换每个元素。
const arrayLike = {
'0': 1,
'1': 2,
'2': 3,
length: 3
};
const actualArray = Array.from(arrayLike, item => item * 2);
// actualArray 将会是 [2, 4, 6]
在这个例子中,映射函数 item => item * 2
被应用于 arrayLike
的每个元素,将每个数字乘以 2。
Set
创建数组当你有一个 Set
对象并希望将其转换为数组时,Array.from()
是一个非常合适的选择。
const set = new Set(['a', 'b', 'c']);
const array = Array.from(set);
// array 将会是 ['a', 'b', 'c']
Map
创建数组同样,Array.from()
也可以从 Map
对象的键或值创建数组。
const map = new Map([['key1', 'value1'], ['key2', 'value2']]);
const keys = Array.from(map.keys());
const values = Array.from(map.values());
// keys 将会是 ['key1', 'key2']
// values 将会是 ['value1', 'value2']
Array.from()
是 JavaScript 中处理集合和数组转换的非常强大的工具,它的灵活性和易用性使其成为日常编程中常用的方法之一。