<?php
abstract class Employee {
	public function __construct($rang = 1, $leader = false) {
		$this->rang = $rang;
		$this->leader = $leader;
 		
		$this->newSolary = $this->calculateSolary();
		$this->newCoffe = $this->calculateCoffe();
		$this->newDocument = $this->calculateDocument();
	}

	public function calculateSolary() {
		switch ($this->rang) {
			case 1:
				$this->newSolary = $this->solary;
			break;

			case 2:
				$this->newSolary = $this->solary + ($this->solary * 0.25);
			break;

			case 3:
				$this->newSolary = $this->solary + ($this->solary * 0.50);
			break;
		}
 
		if ($leader) {
			$this->newSolary = $this->newSolary + ($this->newSolary * 0.50);
		}
 
		return $this->newSolary;	/* Не уверен в необхадимости этой строки, ведь это свойство и так изменяется само по себе. По сему назривают следующие вопросы:
										1. Необхадимо ли передача этого параметра?
										2. Будет ли правильнее создание заместо этого параметра создать обычную переменную внутри функции и далее, её уже передавать?
									*/
	}

	public function calculateCoffe() {
		if ($leader) {
			$this->newCoffe = $this->coffe * 2;
		}

		return $this->newCoffe;
	}

	public function calculateDocument() {
		if ($leader) {
			$this->newDocument = 0;
		}

		return $this->newDocument;
	}
}


class Manager extends Employee {
	public $rang;

	public $solary = 500;
	public $newSolary;

	public $coffe = 20;
	public $newCoffe;

	public $document = 200;
	public $newDocument;

	public $leader;
}

class Marketer extends Employee {
	public $rang;

	public $solary = 400;
	public $newSolary;

	public $coffe = 15;
	public $newCoffe;

	public $document = 150;
	public $newDocument;

	public $leader;
}

class Engineer extends Employee {
	public $rang;

	public $solary = 200;
	public $newSolary;

	public $coffe = 5;
	public $newCoffe;

	public $document = 50;
	public $newDocument;

	public $leader;
}

class Analyst extends Employee {
	public $rang;

	public $solary = 800;
	public $newSolary;

	public $coffe = 50;
	public $newCoffe;

	public $document = 5;
	public $newDocument;

	public $leader;
}

abstract class Department {

	public function __construct() {
		$this->addManagersToDepartment();
		$this->addMarketersToDepartment();
		$this->addEngineersToDepartment();
		$this->addAnalystsToDepartment();
		$this->addLeaderToDepartment();

		$this->calculateEmployeesNumberInDepartment();
		$this->calculateDepartmentExpensesCoffeAndDocuemnt();
		$this->calculateAvargeValue();
	}

	//Здесь смею допусть повторение однотипного кода потому что иначе было бы еще более "муторно", хоть я сам не одобряю такой подход, но тем не мение это всего лишь задачка. 
	public function addManagersToDepartment() {
		foreach ($this->managerNumber as $key => $value) {
			for ($i = 1; $i = $this->managerNumber[$value]; i++) {
				$this->employees[$this->nameOfDepartment]['Managers'][$i] = new Manager($key);
			}
		}			
	}

	public function addMarketersToDepartment() {
		foreach ($this->marketersNumber as $key => $value) {
			for ($i = 1; $i = $this->marketersNumber[$value]; i++) {
				$this->employees[$this->nameOfDepartment]['Marketers'][$i] = new Marketer($key);
			}
		}			
	}

	public function addEngineersToDepartment() {
		foreach ($this->engineerNumber as $key => $value) {
			for ($i = 1; $i = $this->engineerNumber[$value]; i++) {
				$this->employees[$this->nameOfDepartment]['Engineers'][$i] = new Engineer($key);
			}
		}			
	}

	public function addAnalystsToDepartment() {
		foreach ($this->analystNumber as $key => $value) {
			for ($i = 1; $i = $this->analystNumber[$value]; i++) {
				$this->employees[$this->nameOfDepartment]['Analysts'][$i] = new Analyst($key);
			}
		}			
	}

	public function addLeaderToDepartment() {
		switch ($this->departmentLeader["type"]) {
			case 'manager':
				$this->employees[$this->nameOfDepartment]['Leader'][] = new Manager($this->departmentLeader["rang"], true);
			break;

			case 'marketer':
				$this->employees[$this->nameOfDepartment]['Leader'][] = new Marketer($this->departmentLeader["rang"], true);
			break;

			case 'engineer':
				$this->employees[$this->nameOfDepartment]['Leader'][] = new Engineer($this->departmentLeader["rang"], true);
			break;

			case 'analyst':
				$this->employees[$this->nameOfDepartment]['Leader'][] = new Analyst($this->departmentLeader["rang"], true);
			break;
		}
	}

	public function calculateEmployeesNumberInDepartment() {
		$calculateManagersNumber = count($this->employees[$this->nameOfDepartment]['Managers']);
		$calculateMarketersNumber = count($this->employees[$this->nameOfDepartment]['Marketers']);
		$calculateEngineersNumber = count($this->employees[$this->nameOfDepartment]['Engineers']);
		$calculateAnalystsNumber = count($this->employees[$this->nameOfDepartment]['Analysts']);
		$oneLeader = count($this->employees[$this->nameOfDepartment]['Leader']);

		$this->$employeesNumber = $calculateManagersNumber + $calculateMarketersNumber + $calculateEngineersNumber + $calculateAnalystsNumber + $oneLeader;

		return $this->$employeesNumber;
	}

	public function calculateDepartmentExpensesCoffeAndDocuemnt() {
		foreach ($this->employees[$this->nameOfDepartment]['Managers'] as $key => $value) {
			$calculateManagersExpenses += $value->newSolary;
			$calculateManagersCoffe += $value->newCoffe;
			$calculateManagersDocument += $value->newDocument;
		}
		
		foreach ($this->employees[$this->nameOfDepartment]['Marketers'] as $key => $value) {
			$calculateMarketersExpenses += $value->newSolary;
			$calculateMarketersCoffe += $value->newCoffe;
			$calculateMarketersDocument += $value->newDocument;
		}

		foreach ($this->employees[$this->nameOfDepartment]['Engineers'] as $key => $value) {
			$calculateEngineersExpenses += $value->newSolary;
			$calculateEngineersCoffe += $value->newCoffe;
			$calculateEngineersDocument += $value->newDocument;
		}

		foreach ($this->employees[$this->nameOfDepartment]['Analysts'] as $key => $value) {
			$calculateAnalystsExpenses += $value->newSolary;
			$calculateAnalystsCoffe += $value->newCoffe;
			$calculateAnalystsDocument += $value->newDocument;
		}

		foreach ($this->employees[$this->nameOfDepartment]['Leader'] as $key => $value) {
			$calculateLeaderExpenses = $value->newSolary;
			$calculateLeaderCoffe += $value->newCoffe;
			$calculateLeaderDocuments += $value->newDocument;
		}

		$calculateDepartmentExpenses = $calculateManagersExpenses + $calculateMarketersExpenses + $calculateEngineersExpenses + $calculateAnalystsExpenses + $calculateLeaderExpenses;
		$calculateDepartmentCoffe = $calculateManagersCoffe + $calculateMarketersCoffe + $calculateEngineersCoffe + $calculateAnalystsCoffe + $calculateLeaderCoffe;
		$calculateDepartmentDocuments = $calculateManagersDocuments + $calculateMarketersDocuments + $calculateEngineersDocuments + $calculateAnalystsDocuments + $calculateLeaderDocuments;
		
		$this->expenses = array($calculateDepartmentExpenses, $calculateDepartmentCoffe, $calculateDepartmentDocuments);

		return $this->expenses;
	}

	public function calculateAvargeValue() {
		$this->avargeValue = $this->expenses[0] / $this->expenses[2];
	}
}

class Procurement extends Department {
	public $nameOfDepartment = 'Procurement';

	public $employees = array();

	public $managerNumber = array(1 => 9, 2 => 3, 3 => 2);
	public $marketerNumber = array(1 => 2, 2 => 0, 3 => 0);
	public $engineerNumber = array(1 => 0, 2 => 0, 3 => 0);
	public $analystNumber = array(1 => 0, 2 => 0, 3 => 0);
	public $departmentLeader = array("rang" => 2, "type" => 'manager');

	public $employeesNumber;

	public $expenses = array();
	public $avargeValue;
}

class Sales extends Department {
	public $nameOfDepartment = 'Sales';

	public $employees = array();

	public $managerNumber = array(1 => 12, 2 => 0, 3 => 0);
	public $marketerNumber = array(1 => 6, 2 => 0, 3 => 0);
	public $engineerNumber = array(1 => 0, 2 => 0, 3 => 0);
	public $analystNumber = array(1 => 3, 2 => 2, 3 => 0);
	public $departmentLeader = array("rang" => 2, "type" => 'marketer');

	public $employeesNumber;

	public $expenses = array();
	public $avargeValue;
}

class Advertising extends Department {
	public $nameOfDepartment = 'Sales';

	public $employees = array();

	public $managerNumber = array(1 => 8, 2 => 0, 3 => 0);
	public $marketerNumber = array(1 => 15, 2 => 10, 3 => 0);
	public $engineerNumber = array(1 => 2, 2 => 0, 3 => 0);
	public $analystNumber = array(1 => 0, 2 => 0, 3 => 0);
	public $departmentLeader = array("rang" => 3, "type" => 'marketer');

	public $employeesNumber;

	public $expenses = array();
	public $avargeValue;
}

class Logistics extends Department {
	public $nameOfDepartment = 'Sales';

	public $employees = array();

	public $managerNumber = array(1 => 13, 2 => 5, 3 => 0);
	public $marketerNumber = array(1 => 0, 2 => 0, 3 => 0);
	public $engineerNumber = array(1 => 5, 2 => 0, 3 => 0);
	public $analystNumber = array(1 => 0, 2 => 0, 3 => 0);
	public $departmentLeader = array("rang" => 1, "type" => 'manager');

	public $employeesNumber;

	public $expenses = array();
	public $avargeValue;
}