crazycodr / data-transform
此包已被废弃,不再维护。未建议替代包。
用于从可枚举源转换数据
2.0.2
2013-08-22 16:02 UTC
Requires (Dev)
- phpdocumentor/phpdocumentor: 2.*
- phpunit/phpunit: 3.7.*
This package is auto-updated.
Last update: 2022-02-01 12:26:31 UTC
README
此包包含将来自任何可枚举源的实时迭代数据轻松转换的功能。
此类具有一个变换迭代器,并附带不同类,您可以使用这些类从任何可迭代的源转换传入数据。
目录
安装
要安装它,只需将此需求包含到您的composer.json中
{ "require": { "crazycodr/data-transform": "2.*" } }
然后根据需要运行composer install/update。
创建基本变换迭代器
创建变换迭代器至少需要三项
- TransformerContainer,用于包含迭代器的不同变换器
- TransformingIterator,用于迭代数据并提供变换功能
- Transformer,用于将当前数据转换为新的数据
(注意:此代码假设您有一个基于数组的源数据,具有列:姓名、类型、性别和出生日期)
(注意:此代码假设您有一个名为Employe的类,模拟前面的源数据,并有一个新的属性:年龄)
//Create an employee transformer $employeeTransformer = new ClosureTransformer(function($data, $key, $previous){ $result = new Employee(); $result->setName($data['name']); $result->setType($data['type']); $result->setSex($data['sex']); $result->setBirthdate($data['birthdate']); return $result; }); $iterator = new TransformingIterator(new TransformerContainer(), $data); $iterator->addTransformer($employeeTransformer); //Iterate our data source and automatically only get males foreach($iterator as $employee) { echo 'Employee: '.$employee->getName().'<br>'; }
同时支持多个变换器
您可以将许多变换器一次性添加到变换容器中。目标是分离不同的变换方面。
此示例演示第一个变换器创建员工,但第二个手动初始化其他属性。 (年龄与出生日期)请注意,第二个变换器必须使用$previous变量来获取当前变换对象的状态,您不想再次重新创建对象。
//Create an employee transformer $employeeTransformer = new ClosureTransformer(function($data, $key, $previous){ $result = new Employee(); $result->setName($data['name']); $result->setType($data['type']); $result->setSex($data['sex']); $result->setBirthdate($data['birthdate']); return $result; }); $ageCalculatorTransformer = new ClosureTransformer(function($data, $key, $previous){ $birthday = new DateTime($previous->getBirthday()); $interval = $birthday->diff(new DateTime()); $previous->setAge($interval->y); return $previous; }); $iterator = new TransformingIterator(new TransformerContainer(), $data); $iterator->addTransformer($employeeTransformer); $iterator->addTransformer($ageCalculatorTransformer); //Iterate our data source and automatically only get males foreach($iterator as $employee) { echo 'Employee: '.$employee->getName().' is '.$employee->getAge().' years old<br>'; }
在迭代器上下文外使用组件
您不需要使用变换迭代器... ClosureTransformer和TransformerContainer可以在循环外使用。正常使用具体/非具体类构建变换器,并使用一些数据调用"transform"。
//See code in previous snipet $container = new TransformerContainer(); $container->addTransformer($employeeTransformer); $container->addTransformer($ageCalculatorTransformer); $result = $container->transform($data, null);
创建可测试的类
此库的目的是不需要每次都创建迭代器和它们子组件,并且可以轻松测试所有组件。为此,只需创建迭代器和子组件的具体扩展,然后进行测试。
class EmployeeTransformer extends ClosureTransformer { public function __construct() { parent::__construct(function($data, $key, $previous){ $result = new Employee(); $result->setName($data['name']); $result->setType($data['type']); $result->setSex($data['sex']); $result->setBirthdate($data['birthdate']); return $result; }); } }
class EmployeeTransformingIterator extends TransformingIterator { public function __construct($data) { parent::__construct(new TransformerContainer(), $data); $this->addTransformer(new EmployeeTransformer()); } }
这可能看起来有些极端,但这样您就创建了一个具体的功能类,可以重用和测试。请注意,DataProviders是测试组件的好方法,但在测试迭代器时使用它看起来会有些奇怪。
class EmployeeTransformerTest extends PHPUnit_Framework_TestCase { /** * @dataProvider employeeTransformerDataProvider */ public function testTransform($data) { $transformer = new EmployeeTransformer(); $this->assertEquals($data['expected'], $transformer->transform($data['testdata'], null)); } public function employeeTransformerDataProvider() { //To contain the results returned by the data provider $result = array(); //Item 1 $emp = new Employee(); $emp->setName('John doe'); $emp->setBirthdate('1768-01-01'); $emp->setSex('male'); $result[] = array( 'expected' => $emp, 'testdata' => array('name' => 'John doe', 'birthdate' => '1768-01-01', 'sex' => 'male'), ); //Item 2 $emp = new Employee(); $emp->setName('Jane doe'); $emp->setBirthdate('1768-01-01'); $emp->setSex('female'); $result[] = array( 'expected' => $emp, 'testdata' => array('name' => 'Jane doe', 'birthdate' => '1768-01-01', 'sex' => 'female'), ); return $results; } }