如何无限循环数据集字符串

How to infinite loop a dataset string

本文关键字:字符串 数据集 无限循环      更新时间:2023-09-26

我正在寻找一种继续循环几个值的方法。我正在使用一个简单的 ajax 加载脚本,它从目标元素的数据集中获取值(文件)。文件的重新加载每 XXXX 秒发生一次,因此它会一遍又一遍地加载文件,但如果存在更多文件,它应该遍历所有文件,并重新循环它。无限

下面的示例是一个基本的想法,我如何拆分字符串并从第一个字符串开始,但是我如何循环这个(最好的方法),并保持循环。

.HTML

<div id="target" data-load="file1.php | file2.php | file3.php"></div>

jQuery

var fileTo = $('#target').data('widget-load').split("|");
setInterval(function(){
   $('#target').load(fileTo[0])
},1000);

您可以使用setTimeout("function",delay)在自身中继续调用相同的函数,延迟为毫秒。

var fileTo = $('#target').data('widget-load').split("|");
setInterval(function(){
   var file = fileTo.shift();   // `shift` gives the file at 0
   $('#target').load(file);     // load it
   fileTo.push(file);           // `push` adds it at the end of the array
},1000);

@Diode:在无限循环的情况下,shift && push是更好的选择。忘记了他们。在这种情况下,我建议如下:

var intervalId = setInterval((function(theArray)
{
    var target = $('#target');
    var current;
    return function ()
    {
        current = theArray.shift();
        target.load(current);
        theArray.push(current);
    };
})($('#target').data('widget-load').split("|")),1000);

试试这个:

var intervalId = setInterval((function(theArray)
{
    var target = $('#target');//only search for this once, not on every call
    //to make infinite loop, copy the array
    var resetArr = theArray.slice(0);//use slice, if not a reference is assigned and both arrays will be altered 
    //Name is not required, if you want to use a name, pick a better one, next might be reserved (not sure)
    //best go for nextInterval, chose this one for explanation
    return function next()
    {
        //get first element, theArray is now 1 shorter
        target.load(theArray.splice(0,1)[0]);
        if (theArray.length === 0)
        {//no more files left -> this stops the interval
            //clearInterval(intervalId);
            //intervalId = null;
            //restore the array, the loop starts from file1 again --> infinite loop
            theArray = resetArr.slice(0);//copy the original value
        }
    }
})($('#target').data('widget-load').split("|")),1000);

这可能有点密集,但我在chrome控制台中尝试了一个简单的单行版本:

foo = setInterval((function(arr){ return function(){alert(arr.splice(0,1)[0]); if (arr.length === 0){ clearInterval(foo);}};})([1,2,3]),1000);

它就像一个魅力。
工作原理:

intervalId保存区间的 erm id...有点参考。只要设置了,该函数将每1000ms调用一次。我没有将一个简单的函数作为第一个参数传递,而是创建了一个函数,并立即调用它。我传递给无名函数(theArray)的参数可以通过名为next的函数访问,这是匿名函数的返回值。它是在函数内部创建的,因此它可以访问其函数的所有变量,即使在函数返回后也是如此。
这意味着 theArray 的值在其他任何地方都超出了范围,除了 next 函数,这是我们间隔的实际回调。没有什么可以干扰theArray的值,没有任何东西可以被任何外部代码覆盖,这使得与使用全局变量相比,这是一种更安全的方法。
这同样适用于变量 target:它是在匿名函数中声明和初始化的,该函数被调用一次,然后调用 GC'ed。该变量仍然存在,并引用一个jQuery对象。DOM 只搜索过一次,用于该元素,但对 next 函数的每个新调用都可以访问该对象。这样做一次,速度差异很小,一直这样做,你的脚本(很多)更有效率!

所以,间隔:每 1000 毫秒,调用next。它从数组中移动第一个值,该数组是其创建者(该匿名函数)的参数(theArray)。当该数组为空时,将调用 clearInterval 函数来停止该手数。所有文件都已加载,没有继续的意义。
一旦发生这种情况,theArraynext函数和所有其他变量(target)都会超出范围,所以没有全局变量,只有一个漂亮的、干净的内存块,这总是一件好事。我假设此代码将作为事件处理程序的一部分触发,在这种情况下,您只需将其复制粘贴到处理程序中,同样,不会创建全局变量。

如果此代码将成为全局范围的一部分,则只需将其全部包装在自调用函数中即可轻松避免全局:

(function()
{
    var intervalId = setInterval((function(theArray)
    {
        //...
    })($('#target').data('widget-load').split("|")),1000);
})();

一切就绪。恕我直言,这是解决这个问题的最佳、最安全和最 JS 意识的方法。JavaScript 是关于函数的,你越利用它们,语言就越喜欢它。事实上,它会通过揭示它隐藏的表现力来感谢你。

即使您决定不使用此答案,也要阅读诸如闭包以及如何充分利用函数作用域之类的内容。你很快就会发现自己在以全新的方式编写代码,承诺:)

var $target = $('#target'),
    fileTo = $target.data('widget-load').split("|"),
    i = 0;
setInterval(function(){
   $target.load(fileTo[i]);
   i++;
   if (i === fileTo.length)
      i = 0;
},1000);