/*
 * @author Ranides Atterwim <ranides@gmail.com>
 * @copyright Ranides Atterwim
 * @license WTFPL
 * @url http://ranides.net/projects/assira
 */
package net.ranides.assira.collection.suite.maps;

import java.util.ListIterator;
import javax.annotation.Resource;
import net.ranides.assira.collection.maps.ASortedMap;
import net.ranides.assira.collection.suite.IteratorTester;
import net.ranides.assira.collection.suite.sets.SetTester;
import net.ranides.assira.test.TMap;
import net.ranides.assira.test.TMap.TItem;
import net.ranides.assira.test.TMap.TItems;
import net.ranides.assira.junit.TestContract;

/**
 *
 * @author Ranides Atterwim <ranides@gmail.com>
 */
@SuppressWarnings("PMD.MethodNameRules")
public final class ASortedMapTester<K,V> {
    
    @Resource(name = "map!")
    private TMap<K,V> $var;

    @TestContract
    public void basicKeys_Head(ASortedMap<K, V> target) {
        SetTester.assertHead($var.keys(), target.keySet(), $var.list().keys());
        $var.list(4, 7, 5, 3, 6).into(target);
        SetTester.assertHead($var.keys(), target.keySet(), $var.list(3, 4, 5, 6, 7).keys());
    }
    
    @TestContract
    public void basicKeys_Tail(ASortedMap<K, V> target) {
        SetTester.assertTail($var.keys(), target.keySet(), $var.list().keys());
        $var.list(4, 7, 5, 3, 6).into(target);
        SetTester.assertTail($var.keys(), target.keySet(), $var.list(3, 4, 5, 6, 7).keys());
    }
    
    @TestContract
    public void basicKeys_Sub(ASortedMap<K, V> target) {
        SetTester.assertTail($var.keys(), target.keySet(), $var.list().keys());
        $var.list(4, 7, 5, 3, 6).into(target);
        SetTester.assertTail($var.keys(), target.keySet(), $var.list(3, 4, 5, 6, 7).keys());
    }
    
    @TestContract
    public void basicEntries_Head(ASortedMap<K, V> target) {
        SetTester.assertHead($var.entries(), target.entrySet(), $var.list().entries());
        $var.list(4, 7, 5, 3, 6).into(target);
        SetTester.assertHead($var.entries(), target.entrySet(), $var.list(3, 4, 5, 6, 7).entries());
    }
    
    @TestContract
    public void basicEntries_Tail(ASortedMap<K, V> target) {
        SetTester.assertTail($var.entries(), target.entrySet(), $var.list().entries());
        $var.list(4, 7, 5, 3, 6).into(target);
        SetTester.assertTail($var.entries(), target.entrySet(), $var.list(3, 4, 5, 6, 7).entries());
    }
    
    @TestContract
    public void basicEntries_Sub(ASortedMap<K, V> target) {
        SetTester.assertSub($var.entries(), target.entrySet(), $var.list().entries());
        $var.list(4, 7, 5, 3, 6).into(target);
        SetTester.assertSub($var.entries(), target.entrySet(), $var.list(3, 4, 5, 6, 7).entries());
    }
    
    @SuppressWarnings("unchecked")
    @TestContract
    public void basicIterator(ASortedMap<K, V> target) {
        TItems<K,V> list1 = $var.list();
        TItems<K,V> list2 = $var.list(3, 4, 5, 6, 7);
        
        IteratorTester.orderIterator(target.keySet().iterator(), 0, list1.keys());
        IteratorTester.orderIterator(target.entrySet().iterator(), 0, list1.entries());
        IteratorTester.orderIterator((ListIterator)target.values().iterator(), 0, list1.values());
        
        $var.list(4, 7, 5, 3, 6).into(target);
        
        IteratorTester.orderIterator(target.keySet().iterator(), 0, list2.keys());
        IteratorTester.orderIterator(target.entrySet().iterator(), 0, list2.entries());
        IteratorTester.orderIterator((ListIterator)target.values().iterator(), 0, list2.values());
    }
    
    @TestContract
    public void basicIteratorFrom(ASortedMap<K, V> target) {
        TItems<K,V> list1 = $var.list();
        TItems<K,V> list2 = $var.list(3, 4, 5, 6, 7);
        TItem<K,V> item = $var.item(4);
        
        IteratorTester.orderIterator(target.keySet().iterator(item.key()), 0, list1.keys());
        IteratorTester.orderIterator(target.entrySet().iterator(item.entry()), 0, list1.entries());
        
        $var.list(4, 7, 5, 3, 6).into(target);
        
        IteratorTester.orderIterator(target.keySet().iterator(item.key()), 1, list2.keys());
        IteratorTester.orderIterator(target.entrySet().iterator(item.entry()), 1, list2.entries());
    }
    
    @TestContract
    public void basicSubmapIteratorFrom(ASortedMap<K, V> target) {
        TItems<K,V> list = $var.list(3, 4, 5, 6, 7);
        TItem<K,V> item = $var.item(4);

        $var.list(4, 7, 5, 3, 6, 1, 8).into(target);
        ASortedMap<K, V> map = target.subMap($var.item(1).key(), $var.item(8).key());
        
        IteratorTester.subIterator(map.keySet().iterator(item.key()), 2, list.keys());
        IteratorTester.subIterator(map.entrySet().iterator(item.entry()), 2, list.entries());
    }
    
}
