<commit_before>// We assume that we have a separate class for People

// Basic class for all people
var Person={
    // Static vars
    Low: 0,
    Mid: 1,
    Hi: 2,
    
    // the create function
    createNew: function(data){  // data is a Table
        console.log("[People] created.");
        var p={};
        
        // Class vars
        p.type=data.type;               // must be one of Person.types
        p.name=data.name;               // nullable
        p.portIndex=data.portIndex;     // nullable
        p.workplace=null;               // nullable, index of the tile
        p.home=null;                    // nullable, index of the tile
        p.health=0;         // int
        p.education=0;      // int
        p.shelter=0;        // int
        // Class vars (nullable)
        p.influence=(p.type>=Person.Mid?0:null);
        p.role=(p.type>=Person.Mid?0:null);
        p.loyalty=(p.type>=Person.Hi?0:null);

        // Class funcs
        p.nextTurn=function(){return Person.nextTurn(p)};
        p.report=function(){return Person.report(p)};  // Class func: Declaration
        // p.findHousing=function(){return Person.findHousing(p)};

        return p;
    },

    // Class func: Implementation
    nextTurn: function(p){
        // TODO
    },
    
    report: function(p){
        console.log("[Person] type="+p.type+", name="+p.name);
        // TODO: add other infomation that needs to show
    },
    
    // /*global MainGame*/
    // findHousing: function(p){
    //     /*global MainGame*/
    //     var housingIndice=MainGame.board.findBuilding(null,"housing");
    //     console.log("housingIndice"+ housingIndice);

    //     for(var i=0;i<housingIndice.length;i++){
    //         var bld=MainGame.board.at(i);
    //         // found a good place
    //         if(bld.people<bld.maxPeople){
    //             p.home=i;
    //             p.health=bld.health;
    //             p.education=bld.education;
    //             p.shelter=bld.shelter;
    //             bld.people++;
    //             return true;
    //         }
    //     }
    //     return false;
    // },
};

// Contains all the literal information (string/number/bool vars) of all people
var Population={
    // please see stage1.json: it will be created by stage1.population table.
    createNew: function(data){  // data is an Array
        console.log("[Population] created with count:"+data.length);
        console.assert(Array.isArray(data), "[Population] data must be an Array!");
        var pop={};

        // Class vars
        pop.lowList=[];
        pop.midList=[];
        pop.highList=[];

        // Class funcs
        pop.nextTurn=function(){return Population.nextTurn(pop)};
        pop.count=function(){return pop.lowList.length+pop.midList.length+pop.highList.length};
        pop.report=function(){return Population.report(pop)};  // Class func: Declaration
        pop.increase=function(amount){return Population.increase(pop,amount)};
        pop.hire=function(tileIndex,buildingType){return Population.hire(pop,tileIndex,buildingType)};
        pop.fire=function(tileIndex,buildingType){return Population.fire(pop,tileIndex,buildingType)};
        // returns the indice of housed/not housed people in lowList
        pop.findHoused=function(){return Population.findHousingStatus(pop,true)};
        pop.findNotHoused=function(){return Population.findHousingStatus(pop,false)};
        // returns the indice of employed/not employed people in lowList
        pop.findEmployed=function(){return Population.findEmployStatus(pop,true)};
        pop.findNotEmployed=function(){return Population.findEmployStatus(pop,false)};
        // returns the string representation
        pop.toString=function(){return Population.toString(pop)};

        // TODO: add other funcs

        // load the JSON data
        Population.init(pop,data);

        return pop;
    },
    init: function(pop,data){
        console.assert(Array.isArray(data));
        for(var i=0;i<data.length;i++){
            if(data[i].type===Person.Low){
                pop.lowList.push(Person.createNew(data[i]));
            }else if(data[i].type===Person.Mid){
                pop.midList.push(Person.createNew(data[i]));
            }else{
                pop.highList.push(Person.createNew(data[i]));
            }
        }
    },

    // Class func: Implementation
    nextTurn: function(pop){
        for(var p in pop.lowList){
            p.nextTurn();
        }
        for(var p in pop.midList){
            p.nextTurn();
        }
        for(var p in pop.highList){
            p.nextTurn();
        }
        pop.increase(Math.floor(Math.random()*3));
    },
    
    report: function(pop){
        console.log("[Population] now reporting-------");
        for(var i=0;i<pop.length;i++){
            pop[i].report();
        }
        // TODO: add other information that needs to show
        console.log("[Population] end of report.");
    },
    
    increase: function(pop,amount){
        for(var i = 1; i < amount; i += 1){
            var per=Person.createNew({"type":0});
            pop.lowList.push(per);
        }
    },
    
    hire: function(pop,tileIndex){
        /*global MainGame*/
        var bld=MainGame.board.at(tileIndex).getBuilding();
        console.assert(bld);
        // set home for person
        if(bld.name==="apartment"){
            var hl=pop.findNotHoused();
            if(hl.length>0 && bld.people<bld.maxPeople){
                pop.lowList[hl[0]].home=tileIndex;
                return 1;
            }
            return 0;
        }

        // set work place
        var employmentLine = [];
        for(var per in pop.lowList){
            if(per.workplace===null){
                if(MainGame.board.hasRoadConnect(per.home,tileIndex)){
                    employmentLine.push(per);
                }
            }
        }
        if(employmentLine.length > 0){
            employmentLine[MainGame.game.rnd.integer()%employmentLine.length].workplace=tileIndex;
            MainGame.board.children[tileIndex].building.people += 1;
            return 1;
        }
        else{
            return 0;
        }
    },
    
    fire: function(pop,tileIndex){
        /*global MainGame*/
        var bld=MainGame.board.at(tileIndex).getBuilding();
        console.assert(bld);
        // unset home
        if(bld.name==="apartment"){
            var h=pop.findHoused();
            console.log(h);
            for(var i=0;i<h.length;i++){
                if(pop.lowList[h[i]].home===tileIndex){
                    pop.lowList[h[i]].home=null;
                    return 1;
                }
            }
            return 0;
        }

        // unset work place
        var workers = [];
        for(var per in pop.lowList){
            if(per.workplace===tileIndex){
                workers.push(per);
            }
        }
        if(workers.length > 0){
            workers[MainGame.game.rnd.integer()%workers.length].workplace=null;
            MainGame.board.children[tileIndex].building.people -= 1;
            pop.unemployed += 1;
            return 1;
        }
        else{
            return 0;
        }
    },

    findHousingStatus: function(pop, hasHouse){
        var res=[];
        for(var i=0;i<pop.lowList.length;i++)
            if(pop.lowList[i].home!==null && hasHouse 
                || pop.lowList[i].home===null && !hasHouse)
                res.push(i);
        return res;
    },

    findEmployStatus: function(pop, hasWork){
        var res=[];
        for(var i=0;i<pop.lowList.length;i++)
            if(pop.lowList[i].workplace!==null && hasWork 
                || pop.lowList[i].workplace===null && !hasWork)
                res.push(i);
        return res;
    },

    toString: function(pop){
        return "Pop[low,mid,hi]=["+pop.lowList.length+","+pop.midList.length+","+pop.highList.length+"]"
        +" Pop[housed,employed]=["+pop.findHoused().length+","+pop.findEmployed().length+"]";
    }
};<commit_msg>Added at(), getWorkMap() and getHouseMap() to population<commit_after>// We assume that we have a separate class for People

// Basic class for all people
var Person={
    // Static vars
    Low: 0,
    Mid: 1,
    Hi: 2,
    
    // the create function
    createNew: function(data){  // data is a Table
        console.log("[People] created.");
        var p={};
        
        // Class vars
        p.type=data.type;               // must be one of Person.types
        p.name=data.name;               // nullable
        p.portIndex=data.portIndex;     // nullable
        p.workplace=null;               // nullable, index of the tile
        p.home=null;                    // nullable, index of the tile
        p.health=0;         // int
        p.education=0;      // int
        p.shelter=0;        // int
        // Class vars (nullable)
        p.influence=(p.type>=Person.Mid?0:null);
        p.role=(p.type>=Person.Mid?0:null);
        p.loyalty=(p.type>=Person.Hi?0:null);

        // Class funcs
        p.nextTurn=function(){return Person.nextTurn(p)};
        p.report=function(){return Person.report(p)};  // Class func: Declaration
        // p.findHousing=function(){return Person.findHousing(p)};

        return p;
    },

    // Class func: Implementation
    nextTurn: function(p){
        // TODO
    },
    
    report: function(p){
        console.log("[Person] type="+p.type+", name="+p.name);
        // TODO: add other infomation that needs to show
    },
    
    // /*global MainGame*/
    // findHousing: function(p){
    //     /*global MainGame*/
    //     var housingIndice=MainGame.board.findBuilding(null,"housing");
    //     console.log("housingIndice"+ housingIndice);

    //     for(var i=0;i<housingIndice.length;i++){
    //         var bld=MainGame.board.at(i);
    //         // found a good place
    //         if(bld.people<bld.maxPeople){
    //             p.home=i;
    //             p.health=bld.health;
    //             p.education=bld.education;
    //             p.shelter=bld.shelter;
    //             bld.people++;
    //             return true;
    //         }
    //     }
    //     return false;
    // },
};

// Contains all the literal information (string/number/bool vars) of all people
var Population={
    // please see stage1.json: it will be created by stage1.population table.
    createNew: function(data){  // data is an Array
        console.log("[Population] created with count:"+data.length);
        console.assert(Array.isArray(data), "[Population] data must be an Array!");
        var pop={};

        // Class vars
        pop.people=[];

        // Class funcs
        pop.at=function(index){return pop.people[index]};
        pop.nextTurn=function(){return Population.nextTurn(pop)};
        pop.count=function(){return pop.people.length};
        pop.report=function(){return Population.report(pop)};  // Class func: Declaration
        pop.increase=function(amount){return Population.increase(pop,amount)};
        pop.hire=function(tileIndex,buildingType){return Population.hire(pop,tileIndex,buildingType)};
        pop.fire=function(tileIndex,buildingType){return Population.fire(pop,tileIndex,buildingType)};
        // filter people
        // returns the indice of housed/not housed people in lowList
        pop.findHoused=function(){return Population.findHousingStatus(pop,true)};
        pop.findNotHoused=function(){return Population.findHousingStatus(pop,false)};
        // returns the indice of employed/not employed people in lowList
        pop.findEmployed=function(){return Population.findEmployStatus(pop,true)};
        pop.findNotEmployed=function(){return Population.findEmployStatus(pop,false)};
        // returns the workplace table
        pop.getWorkMap=function(){
            var N=MainGame.board.tileCount();
            var map=[];
            for(var i=0;i<N;i++)
                map.push([]);
            pop.people.forEach(function(p,i){
                console.assert(p.workplace!==undefined);
                if(p.workplace!==null)
                    map[p.workplace].push(i);
            });
            return map;
        }
        pop.getHouseMap=function(){
            var N=MainGame.board.tileCount();
            var map=[];
            for(var i=0;i<N;i++)
                map.push([]);
            pop.people.forEach(function(p,i){
                console.assert(p.home!==undefined);
                if(p.home!==null)
                    map[p.home].push(i);
            });
            return map;
        }
        // returns the string representation
        pop.toString=function(){return Population.toString(pop)};

        // TODO: add other funcs

        // load the JSON data
        Population.init(pop,data);

        return pop;
    },
    init: function(pop,data){
        console.assert(Array.isArray(data));
        data.forEach(function(element){
            pop.people.push(Person.createNew(element));
        });
    },

    // Class func: Implementation
    nextTurn: function(pop){
        pop.people.forEach(function(p){p.nextTurn()});
        pop.increase(Math.floor(Math.random()*3));
    },
    
    report: function(pop){
        console.log("[Population] now reporting-------");
        for(var i=0;i<pop.length;i++){
            pop[i].report();
        }
        // TODO: add other information that needs to show
        console.log("[Population] end of report.");
    },
    
    increase: function(pop,amount){
        for(var i = 1; i < amount; i += 1){
            var per=Person.createNew({"type":0});
            pop.people.push(per);
        }
    },
    
    hire: function(pop,tileIndex){
        console.log("work and house map:");
        /*global MainGame*/
        var bld=MainGame.board.at(tileIndex).getBuilding();
        console.assert(bld);
        // set home for person
        if(bld.name==="apartment"){
            var hl=pop.findNotHoused();
            if(hl.length>0 && bld.people<bld.maxPeople){
                pop.people[hl[0]].home=tileIndex;
                return 1;
            }
            return 0;
        }else{
            var hl=pop.findNotEmployed();
            if(hl.length>0 && bld.people<bld.maxPeople){
                pop.people[hl[0]].workplace=tileIndex;
                return 1;
            }
            return 0;
        }
    },
    
    fire: function(pop,tileIndex){
        /*global MainGame*/
        var bld=MainGame.board.at(tileIndex).getBuilding();
        console.assert(bld);
        // unset home
        if(bld.name==="apartment"){
            var h=pop.findHoused();
            console.log(h);
            for(var i=0;i<h.length;i++){
                if(pop.people[h[i]].home===tileIndex){
                    pop.people[h[i]].home=null;
                    return 1;
                }
            }
            return 0;
        }else{
            var h=pop.findEmployed();
            console.log(h);
            for(var j=0;j<h.length;j++){
                if(pop.people[h[j]].workplace===tileIndex){
                    pop.people[h[j]].workplace=null;
                    return 1;
                }
            }
            return 0;
        }
    },

    findHousingStatus: function(pop, hasHouse){
        var res=[];
        pop.people.forEach(function(p,i){
            console.assert(p.home!==undefined);
            if(p.type===Person.Low && (p.home!==null && hasHouse || p.home===null && !hasHouse))
                res.push(i);
        })
        return res;
    },

    findEmployStatus: function(pop, hasWork){
        var res=[];
        pop.people.forEach(function(p,i){
            console.assert(p.workplace!==undefined);
            if(p.type===Person.Low && (p.workplace!==null && hasWork || p.workplace===null && !hasWork))
                res.push(i);
        });
        return res;
    },

    toString: function(pop){
        var stats=[0,0,0];
        pop.people.forEach(function(p){
            stats[p.type]++;
        });
        return "Pop[low,mid,hi]=["+stats[0]+","+stats[1]+","+stats[2]+"]"
        +" Pop[housed,employed]=["+pop.findHoused().length+","+pop.findEmployed().length+"]";
    }
};
{'fraction_non_alphanumeric': 0.1481321395492436, 'fraction_numerical': 0.004631058968817536, 'mean_word_length': 1.784253051401066, 'pattern_counts': {'":': 2, '<': 22, '<?xml version=': 0, '>': 14, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '4053740', 'n_tokens_mistral': 4951, 'n_tokens_neox': 4761, 'n_words': 858}