# Gibbs sampling

# Not by probability but by weight

# string of dimensions and full configurations
# in two lists, one observed, one not observed

# sample not observed dimension D each time
# sample by probability of total weight to D1, D2, D3

from __future__ import division
from __future__ import print_function
from mush import *
import random
import operator


def gibbs_sampling(instance,mask):
    observed = instance[~mask]

    unobserved = instance[mask]

    # print(tttest[0])
    #
    # print("real",observed)
    #
    # print("real",unobserved)
    #
    # print(np.arange(24)[mask])

    guess = {}
    unobserved_index = np.arange(24)[mask]
    for dim in unobserved_index:
        guess[dim] = random.sample(dimension_members[dim], 1)[0]
    # print(guess)

    cnt = 0

    while cnt < 100:

        change_index = random.sample(unobserved_index, 1)[0]

        result = {}
        for i in dimension_members[change_index]:
            result[i] = 0

        for key in guess.keys():
            if key != change_index:
                for i in dimension_members[change_index]:
                    try:
                        result[i] += mushroom[i][guess[key]]['weight']
                    except KeyError:
                        pass
        for node in observed:
            for i in dimension_members[change_index]:
                try:
                    result[i] += mushroom[i][node]['weight']
                except KeyError:
                    pass

        #
        #
        # for node in guess[np.arange(len(guess))!=change_index]:
        #     for i in dimension_members[change_index]:
        #         try:
        #             result[i]+=mushroom[node][i]['weight']
        #         except KeyError:
        #             pass
        #
        # for node in observed:
        #     for i in dimension_members[change_index]:
        #         try:
        #             result[i]+=mushroom[node][i]['weight']
        #         except KeyError:
        #             pass

        resample_node = max(result.iteritems(), key=operator.itemgetter(1))[0]

        if guess[change_index] != resample_node:
            # print('changed', guess[change_index], "into", resample_node)
            cnt = 0
        guess[change_index] = resample_node
        cnt += 1

    # print(guess)

    return guess



totaldims = 24

correct=0
wrong=0

for i in range(len(test)):

    # not none, not all
    # predict whether it's edible. dim 0
    observed_no = random.randint(1, totaldims - 1)
    chosen = np.random.choice(range(1, totaldims), observed_no, replace=False)
    mask = np.ones(totaldims, dtype=bool)
    mask[chosen] = False

    guess=gibbs_sampling(test[i],mask)

    if guess[0]==test[i,0]:
        correct+=1
    else:
        wrong+=1

print(correct,wrong)