如何在 node.js/socket.io 中使用 removeListener 来防止多次触发函数

How to use removeListener in node.js/socket.io to prevent multiple triggered function

我遇到了关于套接字的问题。io/node.js。我将客户端发送到服务器,反之亦然,即使我只触发一次,它也会多次触发我的功能。所以这是我的代码

客户端;

for (var x = circles.length - 1; x >= 0; x--) {
    if (circle.eat(circles[x])) {
        position = {
             x: circles[x].position.x,
             y: circles[x].position.y,
             r: circles[x].position.r,
             index: x
        };
        circles.splice(x, 1);
        socket.emit('eat', position); //Here's the emit to server.
   }
}

服务器端;

var events = require('events');
var eventEmitter = new events.EventEmitter();

socket.on('eat',
    function(data){
    circlePosition.splice(data.index, 1);
    counter++;
    eventEmitter.removeListener('eat', this); //Removing this listener but planning to use it again by adding it again using addListener
});

我已经尝试通过 if else 将传入数据与最近发送的数据进行比较以避免数据重复,即使它会被多次触发但问题仍然存在,如果我使用该方法数据的精度将是一个问题。所以我尝试使用 removeListener 和 addListener 但错误是;

如何摆脱这个?

编辑

我已经尝试让 listen 变量在从客户端发送到服务器后再次变为真,代码如下

客户端:

for (var x = circles.length - 1; x >= 0; x--) {
    if (circle.eat(circles[x])) {
        position = {
            x: circles[x].position.x,
            y: circles[x].position.y,
            r: circles[x].position.r,
            index: x,
                        listen: false   //Condition to if else in server side
        };
        circles.splice(x, 1);
        socket.emit('eat', position); //Here's the emit to server.
    }
}

服务器端:

socket.on('eat', eatFunction);

function eatFunction(data){
    if(!data.listen){   //listen variable used inside the if else block
        circlePosition.splice(data.index, 1);
        counter++;
        data.listen = null;
        console.log(data.listen + " " + counter); //to see if the listen becomes null and the counter to see how many times it triggers
        eventEmitter.removeAllListeners('eat', eatFunction);
    }
}

我认为问题出在客户端,因为它发送的比它应该的多,而不是接收。

看看这一行:

eventEmitter.removeListener('eat', this);

你认为this这里指的是什么对象?好像你认为它指的是功能,但事实并非如此。 JavaScript 中的 this 关键字可能有点棘手,但基本上它会引用包含函数的实例,而不是函数本身。

您需要传递对函数本身的引用。如果您停止使用内联函数并改用命名函数,可能会更容易:

socket.on('eat', eatFunction);

function eatFunction(data){
    circlePosition.splice(data.index, 1);
    counter++;
    eventEmitter.removeListener('eat', eatFunction);
}

请注意 eatFunction() 现在有一个名称,因此您可以将其用作 on()removeListener() 函数的参数。

无耻的自我推销:我写了一篇关于创建 JavaScript 可用函数的教程 here

编辑: 如果你想做的只是对事件做出最高反应,为什么不使用一个变量来跟踪你是否应该对事件做出反应?像这样:

var listen = true;

socket.on('eat', eatFunction);

function eatFunction(data){
    if(listen){
       circlePosition.splice(data.index, 1);
       counter++;
       listen = false;
    }
}