#pragma once
#include "MemMan.h"
#include <stdio.h>

template<class T>
class Vector
{
public:
	Vector(DWORD pid):pid(pid), head(NULL){
		head = (ELEM *)MemMan::Inst().malloc(true, true, pid);
		head->next = NULL;
		count = 0;
	}
	~Vector(void){
	}

	void Add(T e){
		DWORD elemnum = count / ELEM::numperelem;
		ELEM **p = GetElem(elemnum);
		if(count % ELEM::numperelem == 0){
			*p = (ELEM *)MemMan::Inst().malloc(true, true, pid);
		}
		(*p)->a[count % ELEM::numperelem] = e;
		count++;
	}

	T *Get(DWORD index){
		DWORD elemnum = index / ELEM::numperelem;
		ELEM **p = GetElem(elemnum);
		return &(*p)->a[index % ELEM::numperelem];
	}

	T* operator [](size_t i){
		return Get(i);
	}

	DWORD GetCount(){
		return count;
	}

	void Remove(DWORD index){
		for(DWORD i = index; i < count - 1; i++){
			*Get(i) = *Get(i + 1);
		}
		Get(count - 1)->~T();
		count--;
		if(count % ELEM::numperelem == 0){
			DWORD elemnum = index / ELEM::numperelem;
			ELEM **p = GetElem(elemnum);
			MemMan::Inst().free((DWORD)*p);
			*p = NULL;
		}
	}
private:
	DWORD pid;
	struct ELEM{
		ELEM *next;
		static const DWORD numperelem = (PAGE_SIZE - sizeof(ELEM *)) / sizeof(T);
		T a[numperelem];
	};
	ELEM *head;
	DWORD count;

	ELEM **GetElem(DWORD elemnum){
		ELEM **p = &head;
		for(DWORD i = 0; i < elemnum; i++){
			p = &((*p)->next);
		}
		return p;
	}
};

