package MpmasMILPConstraint;
use strict;
use warnings;
use Exporter;
use Storable qw(dclone);
use Data::Dumper;
use MpmasQLModelElementAbstract;

our @ISA = qw(MpmasQLModelElementAbstract);

##class variables

my $lazy_constraint = 0;

sub defaultclass {"constraint"};
sub list_of_default_fields { 
	my @array = qw(name unit eqtype type value);
	return \@array;
}
sub list_of_attribute_fields{
	my @array = qw(othermilp othermilp_subelements name unit eqtype type value range LPRow labgrp epsilon xnproduct perennialconstraint empty sex plot_capacity_layer plot_capacity_with_rented mperiod coefficients lhs slack);
	return \@array;
}
sub list_of_attribute_stubs {
	my @array = qw();
	return \@array;
}
my %defaults = (
	name	=>	"N/A",
	unit	=>	"N/A",
	eqtype	=> 1,
	type	=> "default",
	value 	=> 0,
	mperiod => 0
);
sub get_default_value {
	return $defaults{$_[1]};
}
sub set_default_value {
	$defaults{$_[1]} = $_[2] ;
}

sub lp_row {
	return $_[0]->{LPRow};
}
sub set_lp_row {
	$_[0]->{LPRow} = $_[1];
}
sub type {
	return $_[0]->{type} if (exists  $_[0]->{type}  );
    return $_[0]->get_default_value("type") unless ($MpmasQLModelElementAbstract::donotsetdefaults);
    return undef;
}
sub set_type {
	$_[0]->{type} = $_[1];
}
sub empty {
      return $_[0]->{empty} if (exists  $_[0]->{empty}  );
    return $_[0]->get_default_value("empty") unless ($MpmasQLModelElementAbstract::donotsetdefaults);
    return undef;
}
sub set_empty {
      $_[0]->{empty} = $_[1];
}
sub range {
#    my ($self, $milpid) = @_;
	if (defined $_[1] and $_[1] != $_[0]->standard_milp()) {
	    return $_[0]->{othermilp}->{$_[1]}->{range}  if (defined $_[0]->{othermilp}->{$_[1]}->{range});
	    return -10**31  if ($_[0]->attr("eqtype", $_[1]) == 1);
   	    return 0  if ($_[0]->attr("eqtype", $_[1]) == 3);
  	    return 10**31  if ($_[0]->attr("eqtype", $_[1]) == 2);    
	} 
	else {
        return $_[0]->{range} if (exists $_[0]->{range});
	    return -10**31  if ($_[0]->attr("eqtype") == 1);
        return 0  if ($_[0]->attr("eqtype") == 3);
        return 10**31  if ($_[0]->attr("eqtype") == 2);    
    }
}
sub showsign {
#    my ($self, $milpid) = @_;
	if (defined $_[1] and $_[1] != $_[0]->standard_milp()) {
	    return "'<=" if ($_[0]->attr("eqtype", $_[1]) == 1);
   	    return "'=="  if ($_[0]->attr("eqtype", $_[1]) == 3);
  	    return "'>="  if ($_[0]->attr("eqtype", $_[1]) == 2);    
	} 
	else {

	    return "'<="  if ($_[0]->attr("eqtype") == 1);
        return "'==" if ($_[0]->attr("eqtype") == 3);
        return "'>="  if ($_[0]->attr("eqtype") == 2);    
    }
}

sub calculate_attributes {
#	my $self = $_[0];
	#determine range from eqtype
#	if ($self->attr("eqtype") == 1) {
#		$self->{range} = -10**31 unless (defined $self->{range});
#		$self->{showsign} = "'<=";
#	}
#	elsif ($self->attr("eqtype") == 3) {
#		$self->{range} = 0 unless (defined $self->{range});
#		$self->{showsign} = "'==";
#	}
#	elsif ($self->attr("eqtype") == 2) {
#		$self->{range} = 10**31 unless (defined $self->{range});
#		$self->{showsign} = "'>=";
#	}
#	#same for milps of other agents
#	foreach my $m (keys %{$self->{othermilp} }) {
#		if ($self->attr("eqtype", $m) != $self->attr("eqtype")) {
#			if ($self->attr("eqtype", $m) == 1) {
#				$self->{othermilp}->{$m}->{range} = -10**31 unless (defined $self->{othermilp}->{$m}->{range});
#				$self->{othermilp}->{$m}->{showsign} = "'<=";
#			}
#			elsif ($self->attr("eqtype", $m) == 3) {
#				$self->{othermilp}->{$m}->{range} = 0 unless (defined $self->{othermilp}->{$m}->{range});
#				$self->{othermilp}->{$m}->{showsign} = "'==";
#			}
#			elsif ($self->attr("eqtype", $m) == 2) {
#				$self->{othermilp}->{$m}->{range} = 10**31 unless (defined $self->{othermilp}->{$m}->{range});
#				$self->{othermilp}->{$m}->{showsign} = "'>=";
#			} 
#		}
#	}
}

#FOR MULTIPERIOD PARALLELIZED
sub coeff {
	my ($self,$activity,$milpid) = @_;
	return $self->{othermilp}->{$milpid}->{$activity} if (defined $milpid and $milpid != $self->standard_milp() and defined $self->{othermilp}->{$milpid}->{$activity});
	return $self->{coefficients}->{$activity};
}
sub set_coeff {
	my ($self,$activity,$value, $milpid) = @_;
	if (defined $milpid and $milpid != $self->standard_milp() and defined $self->{othermilp}->{$milpid}->{$activity}) {
	    $self->{othermilp}->{$milpid}->{$activity} = $value ;
	}
	else {
	    $self->{coefficients}->{$activity} = $value;
	}
}
sub coefficients {
	return keys %{$_[0]->{coefficients}};
}
sub lazy_constraint {
    return $lazy_constraint;
}
sub be_lazy {
    $lazy_constraint = 1 ;
}
sub dont_be_lazy {
    $lazy_constraint = 0 ;
}
sub forget_coefficients {
    delete $_[0]->{coefficients};
}
sub transform_coefficients {
    #my ($database, $ActivityRegistry) = @_;
    my $fields = {};
    my $newInserters =  ${$_[0]->{templateref}}->transform_coefficients($_[1], $_[2], $_[0]->{context}, $_[0]->{id}, $fields, $_[0])  ;
    return ($fields, $newInserters);
}

1;
