在 PHP 中对 12 位字符串数组进行数字排序

问题描述 投票:0回答:1

我有一些 PHP 代码,它正在对我的数字数组进行排序。具体数字(例如)如下:

040613002625”, “040613000277”, “040613000511”, “040613001685”, “040613003275”等

但是,当我对值进行排序时,002625 出现在 001685 之前,这是不正确的。

请注意,我在页面上使用分页。我有 190 页,每页列出 30 个项目。分页很可能是问题背后的原因,因为它没有对所有 5,000 个列表进行排序,而是仅读取前 30 个列表并在该单页上进行排序。读取和渲染页面的速度也非常慢(最多 1 分钟)。

这是我现有代码的片段,显示了排序逻辑。看起来正确吗?

$per_page = 30;
$current_page = $this->get_pagenum();
$a = $this->users_data;
$this->users_data = array_slice($a, (($current_page - 1) * $per_page), $per_page);

// call the sorting function
usort($this->users_data, array(&$this, 'usort_reorder'));

// sorting function
function usort_reorder($a, $b)
{
    // if no sort, default to user_login
    $orderby = (!empty($_GET['orderby'])) ? $_GET['orderby'] : 'ID';

    // if no order, default to asc
    $order = (!empty($_GET['order'])) ? $_GET['order'] : 'asc';

    // determine sort order
    $result = strcmp($a[$orderby], $b[$orderby]);
    
    // send final sort direction to usort
    return ($order === 'asc') ? $result : -$result;
}

谢谢。

php usort
1个回答
0
投票

您在排序时遇到的问题可能是因为您使用的是

strcmp
,它用于对字符串而不是数字值进行排序。在这里阅读有关
strcmp
的更多信息:php strcmp 函数。由于您的数字现在在技术上存储为字符串,因此您需要将它们转换为
integers
floats

快速浏览一下,这样的东西应该可以工作:

function usort_reorder($a, $b)
{
    // if no sort, default to user_login
    $orderby = (!empty($_GET['orderby'])) ? $_GET['orderby'] : 'ID';

    // if no order, default to asc
    $order = (!empty($_GET['order'])) ? $_GET['order'] : 'asc';

    // convert string to integer for numeric comparison
    $val1 = intval($a[$orderby]);
    $val2 = intval($b[$orderby]);

    // determine sort order
    if ($val1 < $val2) {
        return ($order === 'asc') ? -1 : 1;
    } elseif ($val1 > $val2) {
        return ($order === 'asc') ? 1 : -1;
    } else {
        return 0;
    }
}

在此功能中:

  1. intval() 用于将值转换为整数。
  2. 函数根据第一个值是否小于、大于或等于第二个值返回 -1、1 或 0

虽然这应该可行,但在数据库查询中对数据进行排序会更有效。看起来像这样:

$per_page = 30;
$current_page = $this->get_pagenum();
$offset = ($current_page - 1) * $per_page;

$query = "SELECT * FROM users ORDER BY CAST(user_id AS UNSIGNED) ASC LIMIT $per_page OFFSET $offset";
© www.soinside.com 2019 - 2024. All rights reserved.