import neuron;

class Adaline(Neuron):
    def __init__(self, n, r=0.8, inf=0):
        super(Adaline, self).__init__(n,r,inf);

    # > Delta-Rule weights adjustment
        # > > l = input label (expected output)
        # > > g = sum (given output)
        # > > returns 'true' if any adjustment was needed, 'false' otherwise
    def adjustment(self, X, l, g):
        print("> Expected: %d; Received: %d" % (l, g));
        if(l != g):
            factor = self.r * (l - g);
            next_val = self.bias + factor * self.noise;
            self.bias = next_val;
            for i in range (0, len(self.W)):
                self.W[i] = self.W[i] + factor * X[i];
            return True;
        return False;

    # > train(X, l): changes the synaptic weights of the artificial neuron based on the input and label
        # > > X = array of binary inputs [-1, 1]
        # > > l = label of the given input
        # > > returns 'true' if there was any adjustment
    def train(self, X, l):
        y = self.classify(X);
        adjust = self.adjustment(X, l, y);
        return adjust;

    def train_set(self, list_X, list_labels):
            # . . While the neuron has to adjust it's weights, keep on training
        any_adjust = True;
        while any_adjust:
            adjust = False;
            for i in range(0, len(list_X)):
                self.debug(DEBUG_W);
                adjust = self.train(list_X[i], list_labels[i]) or adjust;
            self.iterations = self.iterations + 1;
            any_adjust = adjust; # . if adjust is not changed to true, means that the weights are adjusted
