
import {HashMap} from "@nebtex/hashmaps";
import {SymbolElement} from "./symbolElement";

export class SymbolTable {

    /**
     * 符号表的内部数据结构
     */
    private scopeLevelMap:HashMap<any,HashMap<any,SymbolElement>> = new HashMap<any,HashMap<any,SymbolElement>>();


    /**
     * 作用域的初始值
     */
    private initLevel:string = "0";


    /**
     * 向符号表里添加一个域的描述,即进入一个作用域
     */
    public insertTable(parentLevel:string, table:HashMap<any,SymbolElement>):string{
        let currentLevel = this.initLevel;

        if (this.initLevel == parentLevel){
            let i:number = 0;
            while (true){
                i++;
                let tempLevel:string = i.toString();

                if (!this.scopeLevelMap.has(tempLevel)){
                    currentLevel = tempLevel;
                    break;
                }
            }

            this.scopeLevelMap.set(currentLevel,table);
        }else {
            let  i:number = 0;
            while (true){
                i++;
                let tempLevel:string = parentLevel + "::" +i;
                if (!this.scopeLevelMap.has(tempLevel)){
                    currentLevel = tempLevel;
                    break;
                }
            }
            this.scopeLevelMap.set(currentLevel, table);
        }


        return currentLevel;

    }


    /**
     * 从当前作用域中退出
     * @param currentLevel
     */
    public exitTable(currentLevel:string):string | undefined{
        let regex:string = "::";
        let split:string[] = currentLevel.split(regex);
        if (split.length ==1){
            return this.initLevel;
        }

        let end:string = split[split.length - 1];
        let endIndex:number = currentLevel.length - end.length -2;
        let parentLevel:string = currentLevel.substring(0,endIndex);
        if (this.scopeLevelMap.has(parentLevel)){
            return parentLevel;
        }


    }


    /**
     * 根据作用域找到该作用域下的所有变量表
     * @param level
     */
    public getTable(level:string):HashMap<any,SymbolElement>{
        return this.scopeLevelMap.get(level);
    }




    public getInitLevel():string{
        return this.initLevel;
    }


    /**
     * 获取符号表内的作用作用域
     */
    public getAllLevel():IterableIterator<string>{
        return this.scopeLevelMap.keys()
    }


    // public test(){
    //     let symbols = new SymbolTable();
    //     let currentLevel:string = "0";
    //     console.log(currentLevel);
    //     let table:HashMap<any,SymbolElement> = new HashMap<any,SymbolElement>();
    //     currentLevel = symbols.insertTable(currentLevel,table);
    //     console.log(currentLevel);
    //
    //     currentLevel = symbols.insertTable(currentLevel,table);
    //     console.log(currentLevel)
    //
    //     currentLevel = symbols.exitTable(currentLevel);
    //     console.log(currentLevel)
    //
    //
    // }

}

