[JS] 字母异位词分组与JS中对象键值特性

题目地址:LeetCode 49. 字母异位词分组

原题

给你一个字符串数组,请你将 字母异位词 组合在一起。可以按任意顺序返回结果列表。

字母异位词 是由重新排列源单词的所有字母得到的一个新单词。

示例 1:

输入: strs = ["eat", "tea", "tan", "ate", "nat", "bat"]
输出: [["bat"],["nat","tan"],["ate","eat","tea"]]

示例 2:

输入: strs = [""]
输出: [[""]]

示例 3:

输入: strs = ["a"]
输出: [["a"]]

提示:

  • 1 <= strs.length <= 104
  • 0 <= strs[i].length <= 100
  • strs[i] 仅包含小写字母

这道题是一道经典的哈希表应用题,哈希表在这道题里面有两个应用:

  1. 对于一个单词,建立字母到字母出现次数的映射;
  2. 对于题目给定的单词数组,需要建立一个 特殊值 到单词组的映射;

其中的 特殊值 应该满足由单词计算得到,且不同的字母异位词的 特殊值 是相同的。

官方题解

/**
 * @param {string[]} strs
 * @return {string[][]}
 */
var groupAnagrams = function(strs) {
 const map = new Object();
 for (let s of strs) {
 const count = new Array(26).fill(0);
 for (let c of s) {
 count[c.charCodeAt() - 'a'.charCodeAt()]++;
 }
 map[count] ? map[count].push(s) : map[count] = [s];
 }
 return Object.values(map);
};

第一层循环遍历的是词组里的单词。

for(let s of strs){
 const count = new Array(26).fill(0);
 ...
}

一开始我很疑惑,因为对于每一个单词,都新建了一个独立的count来计算这个单词中各个字母出现的次数。

这里的count就是上文说到的特殊值,用来判断字母异位词。

在一个单词遍历完所有字母后,count计算完毕,通过

map[count] ? map[count].push(s) : map[count] = [s];

特殊值 相同的单词分为一组。

我的困惑是每次的count都是新建的数组,每个单词的 特殊值 不同,每个单词都会单独成组。
但事实是

JS 对象特性

根据 JS 的语言特性,对象的key只能是字符串或者Symbol类型。

count作为数组类型,在被当作对象的key使用时,会进行隐式数据类型转换,被转换为一个字符串。

于是,只要有一些单词的字母计数一样,那么它们的count “序列化” 成字符串之后就是相等的。因此,可以被正确地分为一组。


测试

在 Node.js 中测试,使用一个数组作为对象的key来创建一个键值对,输出对象的keys发现自动被转换成字符串了。

作者:feixianxing原文地址:https://www.cnblogs.com/feixianxing/p/18319933/javascript-object-keys-convert-to-string

%s 个评论

要回复文章请先登录注册