using System;
using System.Collections;
using System.Collections.Generic;

public class Set<T> : IEnumerable<T> {
    private Dictionary<T, T> dic = new Dictionary<T, T>();
    
    public Set() {}

    public Set(IEnumerable<T> list) {
        addRange(list);
    }

    public T getUnique(T elem) {
        if (dic.ContainsKey(elem)) {
            return dic[elem];
        }

        dic.Add(elem, elem);
        return elem;
    }

    public void add(T elem) {
        if (contains(elem)) {
            return;
        }

        dic.Add(elem, elem);
    }

    public void addRange(IEnumerable<T> list) {
        foreach(T elem in list) {
            add(elem);
        }
    }

    public bool contains(T elem) {
        return dic.ContainsKey(elem);
    }

	public void remove(T elem) {
		dic.Remove(elem);
	}

    public T getEquivalent(T elem) {
        if (dic.ContainsKey(elem)) {
            return dic[elem];
        }

        return elem;
    }

    public Set<T> intersection(Set<T> other) {
        Set<T> newSet = new Set<T>();

        foreach(T elem in this) {
            if (other.contains(elem)) {
                newSet.add(elem);
            }
        }

        return newSet;
    }

    public int count() {
        return dic.Count;
    }

    public IEnumerator<T> GetEnumerator() {
        return dic.Keys.GetEnumerator();
    }

    IEnumerator IEnumerable.GetEnumerator() {
        return GetEnumerator();
    }

    public List<T> toList() {
        List<T> list = new List<T>();

        foreach (T t in dic.Keys) {
            list.Add(t);
        }

        return list;
    }

    public void clear() {
        dic.Clear();
    }
}
