AWK 数字变量被视为字符串

AWK Numeric Variable treated as string

[Ubuntu 14.04,GNU Awk 4.0.1]

我有一个奇怪的问题...我将从输入文件中检索到的数值分配给自定义变量。当我打印它时,它显示正确,并且打印它的长度显示正确的位数。
但是,当我在循环中使用该变量时,当索引变得大于我的变量的最高有效位时,我的循环停止。

我试过一个For循环,现在一个While循环,都遇到同样的问题。

对于我正在处理的文件,samples 包含值 8092,循环在第 9 次迭代时停止。

#!/usr/bin/awk -f
BEGIN {
  samples = 0;
}
{
  ...
  samples = ;
}
END {
  i = 1;
  while (i <= samples ) {
    if (i>samples) { print "This is the end.\n " i " is bigger than " samples;}
    i++;
  }
}

我是 AWK 的新手,不明白为什么会这样。在阅读了一些教程之后,我的印象是 AWK 能够根据需要在数字的字符串和数字表示之间进行转换。

谁能帮我看看我做错了什么?

解决方案 正如 JNevill & ghoti 所建议的那样,答案是将 0 添加到变量中。在我的例子中,最好的位置就在循环之前,因为 samples` 在 AWK 脚本的主体期间被重写。谢谢

awk 根据变量中保存的值来决定变量的类型。你可以强制它按你想要的方式输入,虽然它有点 hackey(虽然不是全部)。

尝试在执行 for 循环之前将 0 添加到您的变量中。 $sample = $sample + 0,例如。现在,无论 awk 在您点击该行之前怎么想,它现在都会将您的数字视为一个数字,并且您的 for 循环应该按预期执行。

奇怪的是它一直在执行并在 9 次迭代时停止....这表明它可能已经正确处理它并且您可能假设该值为 8092,而实际上它是 9 . 此外,您的 for 循环中打印的位永远不应该执行。希望它不会输出那个。

Awk 并不完全 "convert" 表示之间,它只是使用您提供的任何内容,并根据使用情况调整上下文。因此,在计算布尔值时,任何非零数字的计算结果为 TRUE,除 "0" 之外的任何字符串的计算结果为 TRUE。

我在你的 samples 变量中看不到 真正 的内容,但是如果你想在开始循环之前强制将事物评估为数字,您也许可以简单地将零添加到变量中,即:

samples =  + 0;

此外,如果您的源数据来自 DOS/Windows 机器并且行尾包含回车符 returns (\r\n),并且 </code> 是最后一个字段在每一行,那么您可能会将 <code>i24\r 进行比较,这可能不会给您预期的结果。

要查看输入数据中真正的内容,请尝试:

cat -vet samples | less

如果你在每行末尾的 $ 之前看到 ^M,那么你的输入文件包含回车符 returns,你应该在要求 awk 解析之前适当地处理它它的内容。

事实上,我认为很明显,因为您的输入数据以字符“8”开头,并且您的循环在第 9 次迭代时停止,所以您对 isamples 的比较是一个字符串而不是数字。