From 18298903d15d0bfdb53899aa92a5b38e5616379c Mon Sep 17 00:00:00 2001 From: Petr Kessler Date: Sat, 21 Oct 2023 23:50:40 +0200 Subject: [PATCH] added Vector --- src/Simplex/Math/Vector.php | 61 +++++++++++++++++++++++ src/Simplex/exceptions.php | 9 ++++ src/Simplex/simplex.php | 1 + tests/VectorTest.php | 96 +++++++++++++++++++++++++++++++++++++ 4 files changed, 167 insertions(+) create mode 100644 src/Simplex/Math/Vector.php create mode 100644 tests/VectorTest.php diff --git a/src/Simplex/Math/Vector.php b/src/Simplex/Math/Vector.php new file mode 100644 index 0000000..e20c9ee --- /dev/null +++ b/src/Simplex/Math/Vector.php @@ -0,0 +1,61 @@ + $values */ + public function __construct(array $values) + { + if ($values === []) { + throw new EmptyVectorException; + } + + $this->values = array_map( + static fn ($value): Fraction => Fraction::create($value), + array_values($values), + ); + + $this->size = count($this->values); + } + + + /** @param Vector|array $values */ + public static function create(self|array $values): self + { + return $values instanceof self ? $values : new self($values); + } + + + /** @return Fraction[] */ + public function toArray(): array + { + return $this->values; + } + + + public function count(): int + { + return $this->size; + } +} diff --git a/src/Simplex/exceptions.php b/src/Simplex/exceptions.php index 69e7864..b36fd79 100644 --- a/src/Simplex/exceptions.php +++ b/src/Simplex/exceptions.php @@ -50,5 +50,14 @@ public function __construct() } +final class EmptyVectorException extends SimplexException +{ + public function __construct() + { + parent::__construct('Vector must have at least one value.'); + } +} + + abstract class SimplexException extends \Exception {} diff --git a/src/Simplex/simplex.php b/src/Simplex/simplex.php index cb15c81..a31083e 100644 --- a/src/Simplex/simplex.php +++ b/src/Simplex/simplex.php @@ -17,3 +17,4 @@ require_once __DIR__ . '/exceptions.php'; require_once __DIR__ . '/Math/math.php'; require_once __DIR__ . '/Math/Fraction.php'; +require_once __DIR__ . '/Math/Vector.php'; diff --git a/tests/VectorTest.php b/tests/VectorTest.php new file mode 100644 index 0000000..d6ef106 --- /dev/null +++ b/tests/VectorTest.php @@ -0,0 +1,96 @@ + $values + * @param Fraction[] $expectedValues + * @dataProvider provideCreationData + */ + public function testCreation(array $values, array $expectedValues, int $expectedCount): void + { + $vectorConstructor = new Vector($values); + Assert::equal($expectedValues, $vectorConstructor->toArray()); + Assert::count($expectedCount, $vectorConstructor); + + $vectorFactory = Vector::create($values); + Assert::equal($expectedValues, $vectorFactory->toArray()); + Assert::count($expectedCount, $vectorFactory); + } + + + /** @return array, Fraction[], int}> */ + public function provideCreationData(): array + { + return [ + [ + [1, '2', 3.0, new Fraction('4')], + [new Fraction('1'), new Fraction('2'), new Fraction('3'), new Fraction('4')], + 4, + ], + [ + ['a' => 1, 'b' => '2', 3.0, 'xyz' => new Fraction('4')], + [new Fraction('1'), new Fraction('2'), new Fraction('3'), new Fraction('4')], + 4, + ], + ]; + } + + + public function testEmptyVector(): void + { + Assert::exception(static function (): void { + new Vector([]); + + }, EmptyVectorException::class, 'Vector must have at least one value.'); + + Assert::exception(static function (): void { + Vector::create([]); + + }, EmptyVectorException::class, 'Vector must have at least one value.'); + } + + + /** @dataProvider provideNonNumericElementsData */ + public function testNonNumericElements(string $s): void + { + Assert::exception(static function () use ($s): void { + new Vector([1, 2, $s, 3]); + + }, NonNumericArgumentException::class, sprintf('Non-numeric argument "%s".', $s)); + } + + + /** @return array */ + public function provideNonNumericElementsData(): array + { + return [ + ['asdf'], + [''], + ['0.0.1'], + ['-'], + ['1/2'], + ['-1/2'], + ['1/-2'], + ['-1/-2'], + ]; + } +} + + +(new VectorTest)->run();