根据 2 个参数对对象数组进行分组和排序
我有一组对象,我想根据一个属性对其进行排序,然后根据另一个属性进行“分组”。在下面的示例中,我希望它们根据 $sequence
排序,并根据 $artist
分组。
// 我的类的精简版本:
<?php
class myClass
{
public $sequence;
public $artist;
function __construct($sequence,$artist)
{
$this->sequence=$sequence;
$this->artist=$artist;
}
static function cmp_myclass_sequence($a, $b)
{
$a_seq = $a->sequence;
$b_seq = $b->sequence;
if ($a_seq == $b_seq) {
return 0;
}
return ($a_seq > $b_seq) ? +1 : -1;
}
static function cmp_myclass_artist($a, $b)
{
$a_art = strtolower($a->artist);
$b_art = strtolower($b->artist);
if ($a_art == $b_art) {
return 0;
}
return ($a_art > $b_art) ? +1 : -1;
}
}
//some objects of my class which am using for testing :
$myObj1 = new myClass(1,'A');
$myObj2 = new myClass(1,'B');
$myObj3 = new myClass(1,'C');
$myObj4 = new myClass(2,'A');
$myObj5 = new myClass(2,'B');
$myObj6 = new myClass(2,'C');
$myObj7 = new myClass(4,'A');
$myObj8 = new myClass(5,'A');
$myObj9 = new myClass(3,'B');
$myObj10 = new myClass(3,'G');
$myObj11= new myClass(3,'A');
$myArr=array($myObj1,$myObj2,$myObj3,$myObj4,$myObj5,$myObj6,$myObj7,$myObj8,$myObj9,$myObj10,$myObj11);
echo "My Array Before sort : <br>";
foreach ($myArr as $obj){ print_r($obj); echo "<br>"; }
usort($myArr, array("myClass", "cmp_myclass_sequence"));
//usort($myArr, array("myClass", "cmp_myclass_artist"));
echo "My Array AFTER sort : <br>";
foreach ($myArr as $obj){ print_r($obj); echo "<br>";}
?>
类中的两个排序函数 cmp_myclass_sequence
和 cmp_myclass_artist
各自都能很好地工作。但我不确定如何以这种方式分组数组: 所有 A 级艺术家都排在第一位,然后是 B 级艺术家,依此类推。 在 A 艺术家中,对象应按该对象的序列 int 排序。
简而言之,这就是我正在寻找的结果:
/*
My Array AFTER sort :
myClass Object ( [sequence] => 1 [artist] => A )
myClass Object ( [sequence] => 2 [artist] => A )
myClass Object ( [sequence] => 3 [artist] => A )
myClass Object ( [sequence] => 4 [artist] => A )
myClass Object ( [sequence] => 5 [artist] => A )
myClass Object ( [sequence] => 1 [artist] => B )
myClass Object ( [sequence] => 2 [artist] => B )
myClass Object ( [sequence] => 3 [artist] => B )
myClass Object ( [sequence] => 1 [artist] => C )
myClass Object ( [sequence] => 2 [artist] => C )
myClass Object ( [sequence] => 3 [artist] => G )
*/
I have an array of objects which I want to sort based on one property, and then kind of 'group together' based on another property. In the example below, I would like them sorted based on $sequence
, and grouped based on $artist
.
// a stripped down version of my class :
<?php
class myClass
{
public $sequence;
public $artist;
function __construct($sequence,$artist)
{
$this->sequence=$sequence;
$this->artist=$artist;
}
static function cmp_myclass_sequence($a, $b)
{
$a_seq = $a->sequence;
$b_seq = $b->sequence;
if ($a_seq == $b_seq) {
return 0;
}
return ($a_seq > $b_seq) ? +1 : -1;
}
static function cmp_myclass_artist($a, $b)
{
$a_art = strtolower($a->artist);
$b_art = strtolower($b->artist);
if ($a_art == $b_art) {
return 0;
}
return ($a_art > $b_art) ? +1 : -1;
}
}
//some objects of my class which am using for testing :
$myObj1 = new myClass(1,'A');
$myObj2 = new myClass(1,'B');
$myObj3 = new myClass(1,'C');
$myObj4 = new myClass(2,'A');
$myObj5 = new myClass(2,'B');
$myObj6 = new myClass(2,'C');
$myObj7 = new myClass(4,'A');
$myObj8 = new myClass(5,'A');
$myObj9 = new myClass(3,'B');
$myObj10 = new myClass(3,'G');
$myObj11= new myClass(3,'A');
$myArr=array($myObj1,$myObj2,$myObj3,$myObj4,$myObj5,$myObj6,$myObj7,$myObj8,$myObj9,$myObj10,$myObj11);
echo "My Array Before sort : <br>";
foreach ($myArr as $obj){ print_r($obj); echo "<br>"; }
usort($myArr, array("myClass", "cmp_myclass_sequence"));
//usort($myArr, array("myClass", "cmp_myclass_artist"));
echo "My Array AFTER sort : <br>";
foreach ($myArr as $obj){ print_r($obj); echo "<br>";}
?>
Both the sorting functions that I have in the class, cmp_myclass_sequence
and cmp_myclass_artist
work well on their own. But I am not sure how to get the array grouped in this way :
All the A artists come first, then the B and so on.
Amongst the A artists, the objects should be sorted by the sequence int of that object.
In short this is the result that am looking for :
/*
My Array AFTER sort :
myClass Object ( [sequence] => 1 [artist] => A )
myClass Object ( [sequence] => 2 [artist] => A )
myClass Object ( [sequence] => 3 [artist] => A )
myClass Object ( [sequence] => 4 [artist] => A )
myClass Object ( [sequence] => 5 [artist] => A )
myClass Object ( [sequence] => 1 [artist] => B )
myClass Object ( [sequence] => 2 [artist] => B )
myClass Object ( [sequence] => 3 [artist] => B )
myClass Object ( [sequence] => 1 [artist] => C )
myClass Object ( [sequence] => 2 [artist] => C )
myClass Object ( [sequence] => 3 [artist] => G )
*/
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
您可以使用茴香酒好东西来做到这一点:
http://ouzo.readthedocs.org/en/latest/utils/comparators.html
You can do it with ouzo goodies:
http://ouzo.readthedocs.org/en/latest/utils/comparators.html
您可以使用一个比较函数轻松完成此操作:
You can do this easily with one compare function:
像这样的比较函数怎么样:
这样您就开始按艺术家进行比较,如果艺术家相同,则按顺序进行比较。我认为应该有效。
What about a compare function going like this :
This way you start comparing by artist, and if the artist is the same, you compare by sequence. I think it should work.