我发布了这个问题:How to generate all possible strings, with all ascii chars, to a certain length

可接受的答案有一些漂亮的代码,但是我在理解它时遇到了一些问题。
本质上,如果我要求输出字符串的长度,则其大小始终与其可以输出的最大长度相同。

我猜这是产量*真正引起我一些问题的原因。
当阅读yield *时,它确实说它考虑了最终值。
因此,我更改了以下代码,以突出显示我的问题。

(async function() {
   for(const combo of combinations(5)) {
     console.log(combo.length + "\t" + combo);
     await timer(1);
   }
})();


输出如下:

5      !
5      "
5      #
5      $
5      %
5      &
5      '
5      (
5      )
5      *
5      +
5      ,
5      -
5      .
5      /
5      0
5      1
5      2
5      3
5      4
5      5
5      6
5      7
5      8
5      9
5      :
5      ;


即使字符串只有1个字符,它仍然声明为5。
那么,如何获得生成器发出的ACTUAL值的长度?

最佳答案

您正在获得实际值的长度。这里有两件事:

首先,他们给您的代码仅输出长度为5(或传入的数字)的字符串,而不输出您要求的长度递增的字符串。即,他们给您提供的代码与您的要求不符。如果您想保留生成器的方法,下面的一些代码将输出所有长度为1-5的字符串,尽管我不确定它的顺序是否完全符合您的要求:

function* combinations(length, previous = "") {
  for(const char of chars())
    yield previous + char;

  if (length > 1) {
    for (const char of chars())
      yield* combinations(length - 1, previous + char)
  }
}


其次,字符串看起来少于5个字符的原因是,在可打印字符之前有不可打印字符,而您只能看到可打印字符。例如,算法将使用的第一个字符为String.fromCharCode(0),并且该字符不可打印。



const unprintable = String.fromCharCode(0);
console.log(unprintable);
console.log(JSON.stringify(unprintable));

const longer = unprintable + '!'
console.log(longer);
console.log(JSON.stringify(longer));
console.log(longer.length);

10-06 04:40
查看更多