Переменная получает значение, отличное от назначенного

#javascript

Вопрос:

Привет и извините, если это тривиально, но я уже некоторое время борюсь с этой проблемой. У меня есть эта функция:

 function ParseTeams(rawTeams){
parsedTeams = {};
console.log(parsedTeams);
rawTeams = rawTeams.split("n");

var teamTemplate = {
    "name" : "",
    "team": {}
};

var pokemonTemplate = {
    "pokemon" : "",
    "name" :  "",
    "item" : "",
    "ability": "",
    "moves": {
        "1" : "",
        "2" : "",
        "3" : "",
        "4" : ""
    },
    "nature" : "",
    "evs" : "",
    "gender" : "",
    "ivs" : "",
    "shiny" : "",
    "level" : "",
    "happiness" : ""
};
var blankTemplate = pokemonTemplate;

for(i = 0; i < rawTeams.length; i  ) {
    var data = "";
    var pokemonCount = 0;
    var teamCount = 1;
    var dataCount = 0;
    var nextIsMon = false;

    var gen, teamName;
    for(let c of rawTeams[i]) {
        if(c == "]" amp;amp; !nextIsMon) {                //next data is a pokemon
            if(pokemonCount == 0){                  //this data is gamemode
                if(!parsedTeams[data]){             //check if this hasn't been gamemode has been added
                    parsedTeams[data] = {};
                }
                parsedTeams[data][teamCount] = teamTemplate;
                parsedTeams[data][teamCount].team[1] = blankTemplate;
                gen = data;
                data = "";
                pokemonCount  ;
                nextIsMon = true;
                continue;
            }
        }
        else if(c == "]" amp;amp; nextIsMon) {
            parsedTeams[gen][pokemonCount] = pokemonTemplate;
            pokemonCount  ;
            parsedTeams[gen][pokemonCount], pokemonTemplate = blankTemplate;
            dataCount = 1;
            continue;                
        }
        else if(c == "|") {
            switch(dataCount){
                case(0): parsedTeams[gen][teamCount].name = data; teamName = data; break;
                case(1): pokemonTemplate.pokemon = data;console.log(data);console.log(parsedTeams[gen]); break;
                case(2): pokemonTemplate.name = data; break;
                case(3): pokemonTemplate.item = data; break;
                case(4): pokemonTemplate.ability = data; break;
                case(5): for(z = 1; z < data.split(',').length 1; z  ) {
                            pokemonTemplate.moves[z] = data.split(',')[z-1];
                         }; break;                    
                case(6): pokemonTemplate.nature = data; break;
                case(7): pokemonTemplate.evs = data; break;
                case(8): pokemonTemplate.gender = data; break;
                case(9): pokemonTemplate.ivs = data; break;
                case(10): pokemonTemplate.shiny = data; break;
                case(11): pokemonTemplate.level = data; break;
                case(12): pokemonTemplate.happiness = data; break;
                default: console.log("count out of bounds");
            };
            dataCount  ;
            data = "";
        }
        else data  = c;
    }
    parsedTeams[gen][pokemonCount] = pokemonTemplate;
    pokemonCount = 0;
    teamCount  ;
    data = "";
    nextIsMon = false;
}
return parsedTeams;
}
 

and this is the string passed to the argument

gen8balancedhackmons]Untitled 2|Zacian|||intrepidsword||||||||]Zacian-Crowned||rustedsword|intrepidsword|sunsteelstrike,playrough,glaciallance,stealthrock|Jolly|252,252,252,,252,252|||||]Cinderace||aguavberry|protean|appleacid,anchorshot,agility,aeroblast|Lonely|252,252,252,252,252,252|||||

The problem is that the output looks like this:

 gen8balancedhackmons:
1:
ability: "protean"
evs: "252,252,252,252,252,252"
gender: ""
happiness: ""
item: "aguavberry"
ivs: ""
level: ""
moves: {1: "appleacid", 2: "anchorshot", 3: "agility", 4: "aeroblast"}
name: ""
nature: "Lonely"
pokemon: "Cinderace"
shiny: ""
__proto__: Object
2:
ability: "protean"
evs: "252,252,252,252,252,252"
gender: ""
happiness: ""
item: "aguavberry"
ivs: ""
level: ""
moves: {1: "appleacid", 2: "anchorshot", 3: "agility", 4: "aeroblast"}
name: ""
nature: "Lonely"
pokemon: "Cinderace"
shiny: ""
__proto__: Object
3:
ability: "protean"
evs: "252,252,252,252,252,252"
gender: ""
happiness: ""
item: "aguavberry"
ivs: ""
level: ""
moves: {1: "appleacid", 2: "anchorshot", 3: "agility", 4: "aeroblast"}
name: ""
nature: "Lonely"
pokemon: "Cinderace"
shiny: ""
 

и самая запутанная часть заключается в том, что в консоли.вход в строку 3 выводит точно такой же объект, как и тот, который возвращается в конце кода, несмотря на объявление прямо перед этой строкой.

Что происходит? Сейчас я искренне ничего не понимаю

Комментарии:

1. Позже вы изменяете свой parsedTeams объект, поэтому после входа в консоль он мутирует, и поэтому, когда вы его разворачиваете, отображается измененная версия. Вместо этого вы можете войти JSON.stringify(parsedTeams) в систему, чтобы увидеть статический объект таким, каким он был при выполнении этого LOC.

2. «Проблема в том, что вывод выглядит так:» Можете ли вы объяснить, почему это проблема? Какого результата вы ожидали?

3. Вы понимаете это в следующем ответе?

Ответ №1:

Это потому pokemonTemplate , что вы должны создавать новых pokemonTemplate для каждого покемона. Например

 function ParseTeams(rawTeams){
    parsedTeams = {};
    console.log(parsedTeams);
    rawTeams = rawTeams.split("n");

    var teamTemplate = {
        "name" : "",
        "team": {}
    };

    //Create new template
    var blankTemplate = function(){ 
     return {
        "pokemon" : "",
        "name" :  "",
        "item" : "",
        "ability": "",
        "moves": {
            "1" : "",
            "2" : "",
            "3" : "",
            "4" : ""
        },
        "nature" : "",
        "evs" : "",
        "gender" : "",
        "ivs" : "",
        "shiny" : "",
        "level" : "",
        "happiness" : ""
    }};
    var pokemonTemplate = blankTemplate();

    for(i = 0; i < rawTeams.length; i  ) {
        var data = "";
        var pokemonCount = 0;
        var teamCount = 1;
        var dataCount = 0;
        var nextIsMon = false;

        var gen, teamName;
        for(let c of rawTeams[i]) {
            if(c == "]" amp;amp; !nextIsMon) {                //next data is a pokemon
                if(pokemonCount == 0){                  //this data is gamemode
                    if(!parsedTeams[data]){             //check if this hasn't been gamemode has been added
                        parsedTeams[data] = {};
                    }
                    parsedTeams[data][teamCount] = teamTemplate;
                    parsedTeams[data][teamCount].team[1] = blankTemplate();
                    gen = data;
                    data = "";
                    pokemonCount  ;
                    nextIsMon = true;
                    continue;
                }
            }
            else if(c == "]" amp;amp; nextIsMon) {
                parsedTeams[gen][pokemonCount] = pokemonTemplate;
                pokemonCount  ;
                parsedTeams[gen][pokemonCount], pokemonTemplate = blankTemplate();
                dataCount = 1;
                continue;                
            }
            else if(c == "|") {
                switch(dataCount){
                    case(0): parsedTeams[gen][teamCount].name = data; teamName = data; break;
                    case(1): pokemonTemplate.pokemon = data;console.log(data);console.log(parsedTeams[gen]); break;
                    case(2): pokemonTemplate.name = data; break;
                    case(3): pokemonTemplate.item = data; break;
                    case(4): pokemonTemplate.ability = data; break;
                    case(5): for(z = 1; z < data.split(',').length 1; z  ) {
                                pokemonTemplate.moves[z] = data.split(',')[z-1];
                             }; break;                    
                    case(6): pokemonTemplate.nature = data; break;
                    case(7): pokemonTemplate.evs = data; break;
                    case(8): pokemonTemplate.gender = data; break;
                    case(9): pokemonTemplate.ivs = data; break;
                    case(10): pokemonTemplate.shiny = data; break;
                    case(11): pokemonTemplate.level = data; break;
                    case(12): pokemonTemplate.happiness = data; break;
                    default: console.log("count out of bounds");
                };
                dataCount  ;
                data = "";
            }
            else data  = c;
        }
        parsedTeams[gen][pokemonCount] = pokemonTemplate;
        pokemonCount = 0;
        teamCount  ;
        data = "";
        nextIsMon = false;
    }
    return parsedTeams;
}

ParseTeams("gen8balancedhackmons]Untitled 2|Zacian|||intrepidsword||||||||]Zacian-Crowned||rustedsword|intrepidsword|sunsteelstrike,playrough,glaciallance,stealthrock|Jolly|252,252,252,,252,252|||||]Cinderace||aguavberry|protean|appleacid,anchorshot,agility,aeroblast|Lonely|252,252,252,252,252,252|||||")
 

В вашем первоначальном подходе использовался тот же объект pokemonTemplate. На самом деле, существует только один объект pokemonTemplate, поэтому 1, 2, 3 имеют одинаковые значения.