【问题标题】:indexOf / includes don't do an exact match and return false positivesindexOf / 包含不进行完全匹配并返回误报
【发布时间】:2020-09-07 20:04:20
【问题描述】:

我想构建一个 if 语句,其中 if 标准基于一个变量是否等于多个值的 any 的相等性测试。但是,我不想对测试值进行硬编码,而是传递一个之前随机子集的值数组。

首先,我通过对 15 个值的数组中的 5 个值进行子集化/采样来获得一组随机值。基本上,我使用的是this excellent solution

function getRandomSubarray(arr, size) {
    var shuffled = arr.slice(0), i = arr.length, temp, index;
    while (i--) {
        index = Math.floor((i + 1) * Math.random());
        temp = shuffled[index];
        shuffled[index] = shuffled[i];
        shuffled[i] = temp;
    }
    return shuffled.slice(0, size);
}

var x = [1,2,3,4,5,6,7,8,9,10,11,12,13,14,15];
var fiveRandomMembers = getRandomSubarray(x, 5);

那么,我想通过fiveRandomMembers来测试一个变量是否等于fiveRandomMembers的数组中的任何值。然后做点什么。为此,我想使用this solution

var L = function()
{
    var obj = {};
    for(var i=0; i<arguments.length; i++)
        obj[arguments[i]] = null;

    return obj;
};

if(foo in L(fiveRandomMembers)) {
/// do something
};

不幸的是,这对我不起作用。我必须承认,此代码的实现是在 Qualtrics 调查中进行的,因此问题可能与 Qualtrics 平台有细微差别,这就是它对我不起作用的原因。我是 JavaScript 的新手,所以如果这是一个微不足道的问题,我深表歉意。但我相信我的代码即使在纯 JavaScript 中也存在问题(也就是说,不管 Qualtrics 是什么),我想找出原因。

2020 年 5 月 24 日更新

我对此进行了更深入的研究,并且有了一些见解。这看起来更像是一个 qualtrics 问题,而不是简单的 JS 问题。然而,潜在的问题可能仍然与一些 JS 机制有关,这就是为什么我费心在这里更新它——也许有人会知道是什么导致了这种行为。

回顾一下——我想根据给定变量的内容是否与数组中的 either 值匹配来调整操作。我试过同时使用includesindexOf,但任何一种方法都失败了。问题归结为函数没有进行 exact 匹配。例如,如果我有一个由 5 个数字组成的数组,例如8, 9, 12, 13, 14,并且我想测试数组中是否存在4,那么完全匹配应该返回FALSE。但是,indexOfcontains 都返回TRUE,因为14 中包含4。这不是一个精确的匹配。此外,我试图调查indexOf 会为这种误报匹配返回什么位置。通常,它会返回一个甚至大于数组总长度的位置,这毫无意义。以下是我的 Qualtrics 调查中的一个示例,证明了问题:

给出这个的代码由两个质量问题组成:

(-) 第一段

Qualtrics.SurveyEngine.addOnReady(function()
{
    /*Place your JavaScript here to run when the page is fully displayed*/

    function getRandomSubarray(arr, size) {
    var shuffled = arr.slice(0), i = arr.length, temp, index;
    while (i--) {
        index = Math.floor((i + 1) * Math.random());
        temp = shuffled[index];
        shuffled[index] = shuffled[i];
        shuffled[i] = temp;
    }
    return shuffled.slice(0, size);
}

var x = [1,2,3,4,5,6,7,8,9,10,11,12,13,14,15];
var fiveRandomMembers = getRandomSubarray(x, 5);

if (Array.isArray(fiveRandomMembers)) Qualtrics.SurveyEngine.setEmbeddedData('is_array', "TRUE");


Qualtrics.SurveyEngine.setEmbeddedData('length', fiveRandomMembers.length);


Qualtrics.SurveyEngine.setEmbeddedData('five_sampled_numbers', fiveRandomMembers);

});

(-) 第二段

Qualtrics.SurveyEngine.addOnReady(function()
{
    jQuery("#"+this.questionId).find('.QuestionText:first').css("padding-bottom", "0px");


var currentLoopNum = "${lm://CurrentLoopNumber}";
    // var currentLoopNum = parseInt(currentLoopNum, 10); // tried converting to numeric but it doesn't solve the problem
var fiveSampledNumbers = "${e://Field/five_sampled_numbers}";

if (fiveSampledNumbers.includes(currentLoopNum)) {
   Qualtrics.SurveyEngine.setEmbeddedData('does_loop_number_appear', "Yes");
} else {
    Qualtrics.SurveyEngine.setEmbeddedData('does_loop_number_appear', "No");

}
    Qualtrics.SurveyEngine.setEmbeddedData('index_of', fiveSampledNumbers.indexOf(currentLoopNum));

});

这是 Qualtrics 调查的链接,用于演示问题,以防有助于故障排除link


但是,在 Qualtrics 之外测试相同代码时,问题不会重现。

是否有人有线索甚至假设匹配可能存在什么问题?即使您不一定熟悉 Qualtrics...

【问题讨论】:

  • 能否提供 qualtrics 网站的链接,以便我们自己测试?
  • 另外,如果您能包含 qualtrics 屏幕截图中使用的代码,那就太好了。
  • @marco-a,谢谢——我用 JS 代码更新了帖子,并提供了 Qualtrics 调查的链接。

标签: javascript arrays indexof qualtrics


【解决方案1】:

我以前从未与 Qualtrics 合作过,但对我来说,这条线很明显

var fiveSampledNumbers = "${e://Field/five_sampled_numbers}";

将为fiveSampledNumbers分配一个字符串值,而不是一个数组值。

确实,如果您尝试对字符串而不是数组进行检查,则会得到上面看到的意外结果,因为您执行的是字符串操作而不是数组操作:

var fiveSampledNumbers = "6,4,10,11,15";
console.log(fiveSampledNumbers.includes(5));  // logs true (string ends with the character "5")
console.log(fiveSampledNumbers.indexOf(5));   // logs 11   (index of the character "5")

要解决这个问题,您必须用逗号分隔字符串并解析其中的每个数字:

var fiveSampledNumbers = "6,4,10,11,15";
fiveSampledNumbers = fiveSampledNumbers.split(",").map(function (n) { return parseInt(n, 10); });
console.log(fiveSampledNumbers.includes(5));  // logs false
console.log(fiveSampledNumbers.indexOf(5));   // logs -1

【讨论】:

  • 啊哈!我知道了。有没有办法将解析的数字集重建为数组?还是直接把原字符串转成数组?
  • @Emman:最后一个 sn-p 代码的第二行就是这样做的。
猜你喜欢
  • 1970-01-01
  • 2015-03-12
  • 2022-06-15
  • 2019-10-03
  • 1970-01-01
  • 1970-01-01
  • 2021-06-28
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多