Java TreeSet Solution 
\nclass ExamRoom {\n    // TreeSet keeps numbers in ascending order\n    private TreeSet<Integer> seats = new TreeSet<>();\n    private int length;\n    \n    p
```\nclass ExamRoom {\n    // TreeSet keeps numbers in ascending order\n    private TreeSet<Integer> seats = new TreeSet<>();\n    private int length;\n    \n    public ExamRoom(int N) {\n        this.length = N;\n    }\n    \n    public int seat() {\n        // First student always sits at seats[0]\n        if(seats.size() == 0){\n            seats.add(0);\n            return 0;\n        }\n        int left = 0, distance = Integer.MIN_VALUE, res = -1, curDistance;\n        // This for-loop supposes seats[0] and seats[length - 1] have already been taken,\n        // and looks for the seat which has maximum distance to the closest occupied seats at its left and right\n        for(int curIndex : seats){\n            curDistance = (curIndex - left) / 2;\n            if( curDistance > distance ){\n                res = left + curDistance;\n                distance = curDistance;\n            } \n            left = curIndex;\n        }\n        \n        // Since the for-loop always supposes that seats[0] and seats[length - 1] are occupied\n        // We need to check if the seats[length - 1] is occupied and see if it is the best option\n        if(!seats.contains(length - 1)){\n            curDistance = length - left - 1;\n            if(curDistance > distance){\n                res = left + curDistance;\n                distance = curDistance;\n            }\n        }\n        // Same here, we need to check whether seats[0] is occupied and see if it\'s the best option\n        if(!seats.contains(0)){\n            curDistance = seats.ceiling(0);\n            if(curDistance >= distance)\n                res = 0;\n        }\n        seats.add(res);\n        return res;\n    }\n    \n    public void leave(int p) {\n        seats.remove(p);\n    }\n}\n```
[]