From 51f45c0f281ea0c1722acb79751e227ba77a2b6a Mon Sep 17 00:00:00 2001 From: mark_story Date: Sat, 14 Jan 2012 22:47:44 -0500 Subject: [PATCH] Moving flatten() across. It is no longer recursive either. --- lib/Cake/Test/Case/Utility/Set2Test.php | 55 +++++++++++++++++++++++++ lib/Cake/Utility/Set2.php | 36 +++++++++++++++- 2 files changed, 90 insertions(+), 1 deletion(-) diff --git a/lib/Cake/Test/Case/Utility/Set2Test.php b/lib/Cake/Test/Case/Utility/Set2Test.php index 735916fa4f9..3be7b1676bf 100644 --- a/lib/Cake/Test/Case/Utility/Set2Test.php +++ b/lib/Cake/Test/Case/Utility/Set2Test.php @@ -221,4 +221,59 @@ public function testMaxDimensions() { $this->assertEquals($result, 5); } +/** + * Tests Set::flatten + * + * @return void + */ + public function testFlatten() { + $data = array('Larry', 'Curly', 'Moe'); + $result = Set2::flatten($data); + $this->assertEquals($result, $data); + + $data[9] = 'Shemp'; + $result = Set2::flatten($data); + $this->assertEquals($result, $data); + + $data = array( + array( + 'Post' => array('id' => '1', 'author_id' => '1', 'title' => 'First Post'), + 'Author' => array('id' => '1', 'user' => 'nate', 'password' => 'foo'), + ), + array( + 'Post' => array('id' => '2', 'author_id' => '3', 'title' => 'Second Post', 'body' => 'Second Post Body'), + 'Author' => array('id' => '3', 'user' => 'larry', 'password' => null), + ) + ); + + $result = Set2::flatten($data); + $expected = array( + '0.Post.id' => '1', + '0.Post.author_id' => '1', + '0.Post.title' => 'First Post', + '0.Author.id' => '1', + '0.Author.user' => 'nate', + '0.Author.password' => 'foo', + '1.Post.id' => '2', + '1.Post.author_id' => '3', + '1.Post.title' => 'Second Post', + '1.Post.body' => 'Second Post Body', + '1.Author.id' => '3', + '1.Author.user' => 'larry', + '1.Author.password' => null + ); + $this->assertEquals($expected, $result); + + $data = array( + array('Post' => array('id' => 1)), + array('Post' => array('id' => 2)), + ); + $result = Set2::flatten($data, '/'); + $expected = array( + '0/Post/id' => '1', + '1/Post/id' => '2', + ); + $this->assertEquals($expected, $result); + } + } diff --git a/lib/Cake/Utility/Set2.php b/lib/Cake/Utility/Set2.php index 17d4a0f17ad..ea59c9796ea 100644 --- a/lib/Cake/Utility/Set2.php +++ b/lib/Cake/Utility/Set2.php @@ -82,8 +82,42 @@ public static function filter(array $data) { } - public static function flatten(array $data) { +/** + * Collapses a multi-dimensional array into a single dimension, using a delimited array path for + * each array element's key, i.e. array(array('Foo' => array('Bar' => 'Far'))) becomes + * array('0.Foo.Bar' => 'Far'). + * + * @param array $data Array to flatten + * @param string $separator String used to separate array key elements in a path, defaults to '.' + * @return array + * @link http://book.cakephp.org/2.0/en/core-utility-libraries/set.html#Set::flatten + */ + public static function flatten(array $data, $separator = '.') { + $result = array(); + $stack = array(); + $path = null; + reset($data); + while (!empty($data)) { + $key = key($data); + $element = $data[$key]; + unset($data[$key]); + + if (is_array($element)) { + if (!empty($data)) { + $stack[] = array($data, $path); + } + $data = $element; + $path .= $key . $separator; + } else { + $result[$path . $key] = $element; + } + + if (empty($data) && !empty($stack)) { + list($data, $path) = array_pop($stack); + } + } + return $result; } public static function merge(array $data, $merge) {