Я пытаюсь сделать некоторую простую браузерную игру, используя p5.js. И я столкнулся с проблемой:
У меня есть множество зомби. Объект Zombie имеет метод getanswer(), который возвращает число. Я пытаюсь сделать функцию addzombie(), которая подталкивает один новый зомби к массиву. Проблема в том, что я не хочу повторять ответы в массиве. Это моя текущая функция:
function mkex(){
var values = []
for (i=1;i<11;i++){
values.push(i);
}
var signs = ['+','-','/','*'];
var result = -1;
var a = 0;
var b = 0;
var c = 0;
var sign1 = "";
var sign2 = "";
while (result<=0){
a = values[Math.round(Math.random()*(values.length-1))];
b = values[Math.round(Math.random()*(values.length-1))];
c = values[Math.round(Math.random()*(values.length-1))];
sign1 = signs[Math.round(Math.random()*(signs.length-1))];
sign2 = signs[Math.round(Math.random()*(signs.length-1))];
switch(sign1){
case "+":
switch(sign2){
case "+":
result=a+b+c;
break;
case "-":
result=a+b-c;
break;
case "/":
if (b%c==0){
result=a+b/c;
}
break;
case "*":
result=a+b*c;
break;
default:
break;
}
break;
case "-":
switch(sign2){
case "+":
result=a-b+c;
break;
case "-":
result=a-b-c;
break;
case "/":
if (b%c==0){
result=a-b/c;
}
break;
case "*":
result=a-b*c;
break;
default:
break;
}
break;
case "/":
switch(sign2){
case "+":
if (a%b==0){
result=a/b+c;
}
break;
case "-":
if (a%b==0){
result=a/b-c;
}
break;
case "/":
if (a%b==0){
if (a/b%c==0){
result=a/b/c;
}
}
break;
case "*":
if (a%b==0){
result=a/b*c;
}
break;
default:
break;
}
break;
case "*":
switch(sign2){
case "+":
result=a*b+c;
break;
case "-":
result=a*b-c;
break;
case "/":
if (a*b%c==0){
result=a*b/c;
}
break;
case "*":
result=a*b*c;
break;
default:
break;
}
break;
default:
break;
}
}
var expr = ""+a+sign1+b+sign2+c;
var ret = [expr, result];
return ret;
}
function addzombie(){
var expr = mkex();
if (zombies.length==0){
zombies.push(new Zombie(player.getxy(),expr));
} else{
for (i=0;i<zombies.length;i++){
if (zombies[i].getanswer()==expr[1]){
addzombie();
}
zombies.push(new Zombie(player.getxy(),expr));
}
}
Функция mkex() возвращает массив, содержащий строку и ответ. Зомби нуждается в координатах игрока, чтобы отбросить его от игрока.
Эта функция не работает, у меня все еще есть зомби с одинаковыми ответами. Может кто-нибудь, пожалуйста, скажите мне, что не так?
Использование Set
для отслеживания ответов упростит и ускорит решение (поскольку среднее время поиска в Set
равно O(1)
)
let answerSet = new Set();
let zombies = [];
function addZombie() {
let expr = mkex();
let zombie = new Zombie(player.getxy(),expr);
while(answerSet.has(zombie.getanswer())) {
zombie = new Zombie(player.getxy(),expr);
}
answerSet.add(zombie.getanswer());
zombies.push(zombie);
}
i
и рекурсию одновременно => плохо . Во-вторых: это может повториться навсегда (ну, пока вы не исчерпаете стек и не получите ошибку) в зависимости от того, как работаетmkex
.