Custom Alphabetical Sort回调函数的Laravel部分

huangapple go评论63阅读模式
英文:

Laravel Custom Alphabetical Sort callback function

问题

I have a collection of items (shirts) that could be a various range of sizes. The order of the sizes should be as follows.

XS1, XS3, ... S1, S3, ... M1, M3, ... L1, L3, ... XL1, XL3, ... 2XL1, ... 3XL1, ...

Right now when I run the sort,

$items->sortBy('size')

It outputs the results as

2XL#, 3XL#, L#, M#, S# XL#, XS#

which makes sense because that is the natural sort based on alphabetical and numerical orders.

What would be the best way to write a callback function to sort by my specific order needed?

英文:

I have a collection of items (shirts) that could be a various range of sizes. The order of the sizes should be as follows.

XS1, XS3, ... S1, S3, ... M1, M3, ... L1, L3, ... XL1, XL3, ... 2XL1, ... 3XL1, ...

Right now when I run the sort,

$items->sortBy('size')

It outputs the results as

2XL#, 3XL#, L#, M#, S# XL#, XS#

which makes sense because that is the natural sort based on alphabetical and numerical orders.

What would be the best way to write a callback function to sort by my specific order needed?

答案1

得分: 3

以下是您要翻译的内容:

"Shy of modifying your schema so that you can perform the sorting server-side, the various sort methods of the Illuminate Collection class take an optional callable as an argument so that you can provide your own sorting mechanism. Using this, you could define an array of the various sizes you have, in the order that you want them to appear, and then use the position of the target string in that array as your sort comparator:

这段文字描述了使用 Illuminate Collection 类的各种排序方法时,可以提供可选的可调用函数作为参数,以便提供自定义的排序机制。您可以使用这种方式定义一个包含各种尺寸的数组,按照您希望它们出现的顺序排列,并使用目标字符串在该数组中的位置作为排序比较器:"

$collection = collect([
    ['id' => 1, 'size' => 'S3'],
    ['id' => 2, 'size' => 'M1'],
    ['id' => 3, 'size' => 'XS1'],
    ['id' => 4, 'size' => '3XL1'],
    ['id' => 5, 'size' => 'S1'],
]);

$sorted = $collection->sortBy([
    function($a, $b) {
        $order = ['XS1', 'XS3', 'S1', 'S3', 'M1', 'L1', 'L3', 'XL1', 'XL3', '2XL1', '3XL1'];
        return array_search($a['size'], $order) <=> array_search($b['size'], $order);
    }
]);

print_r($sorted->toArray());

这段代码示例展示了如何使用 Illuminate Collection 类进行排序,并提供了一个自定义排序机制的示例。排序结果如下:

Array
(
    [0] => Array
        (
            [id] => 3
            [size] => XS1
        )

    [1] => Array
        (
            [id] => 5
            [size] => S1
        )

    [2] => Array
        (
            [id] => 1
            [size] => S3
        )

    [3] => Array
        (
            [id] => 2
            [size] => M1
        )

    [4] => Array
        (
            [id] => 4
            [size] => 3XL1
        )

)

或者(稍微更高效的方法)您可以将排序数组设为关联数组,其中键是尺寸,值是排序顺序:

$sorted = $collection->sortBy([
    function($a, $b) {
        $order = [
            'XS1' => 0,
            'S1' => 1,
            'S3' => 2,
            'M1' => 3,
            '3XL1' => 4,
        ];
        return $order[$a['size']] <=> $order[$b['size']];
    }
]);
英文:

Shy of modifying your schema so that you can perform the sorting server-side, the various sort methods of the Illuminate Collection class take an optional callable as an argument so that you can provide your own sorting mechanism. Using this, you could define an array of the various sizes you have, in the order that you want them to appear, and then use the position of the target string in that array as your sort comparator:

$collection = collect([
    [&#39;id&#39; =&gt; 1, &#39;size&#39; =&gt; &#39;S3&#39;],
    [&#39;id&#39; =&gt; 2, &#39;size&#39; =&gt; &#39;M1&#39;],
    [&#39;id&#39; =&gt; 3, &#39;size&#39; =&gt; &#39;XS1&#39;],
    [&#39;id&#39; =&gt; 4, &#39;size&#39; =&gt; &#39;3XL1&#39;],
    [&#39;id&#39; =&gt; 5, &#39;size&#39; =&gt; &#39;S1&#39;],
]);

$sorted = $collection-&gt;sortBy([
    function($a, $b) {
        $order = [&#39;XS1&#39;, &#39;XS3&#39;, &#39;S1&#39;, &#39;S3&#39;, &#39;M1&#39;, &#39;L1&#39;, &#39;L3&#39;, &#39;XL1&#39;, &#39;XL3&#39;, &#39;2XL1&#39;, &#39;3XL1&#39;];
        return array_search($a[&#39;size&#39;], $order) &lt;=&gt; array_search($b[&#39;size&#39;], $order);
    }
]);

print_r($sorted-&gt;toArray());

This yields:

Array
(
    [0] =&gt; Array
        (
            [id] =&gt; 3
            [size] =&gt; XS1
        )

    [1] =&gt; Array
        (
            [id] =&gt; 5
            [size] =&gt; S1
        )

    [2] =&gt; Array
        (
            [id] =&gt; 1
            [size] =&gt; S3
        )

    [3] =&gt; Array
        (
            [id] =&gt; 2
            [size] =&gt; M1
        )

    [4] =&gt; Array
        (
            [id] =&gt; 4
            [size] =&gt; 3XL1
        )

)

Alternatively (and slightly more performant) you could make your sort array associative with the key as the size and the value as the sort order:

$sorted = $collection-&gt;sortBy([
    function($a, $b) {
        $order = [
            &#39;XS1&#39; =&gt; 0,
            &#39;S1&#39; =&gt; 1,
            &#39;S3&#39; =&gt; 2,
            &#39;M1&#39; =&gt; 3,
            &#39;3XL1&#39; =&gt; 4,
        ];
        return $order[$a[&#39;size&#39;]] &lt;=&gt; $order[$b[&#39;size&#39;]];
    }
]);

huangapple
  • 本文由 发表于 2023年5月18日 04:25:32
  • 转载请务必保留本文链接:https://go.coder-hub.com/76275956.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定