You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

PHP中按特定规则合并两个不同大小的关联数组

数组合并需求与解决方案

需求说明

以第一个数组的日期键为基准,与第二个数组的日期键匹配:

  • 匹配成功时,保留第二个数组对应日期的详情数据
  • 未匹配的日期,填充固定结构[1 => '']

示例数组

$first = [
    '2022-10-23' => '2022-10-23',
    '2022-10-24' => '2022-10-24',
    '2022-10-25' => '2022-10-25',
    '2022-10-26' => '2022-10-26',
    '2022-10-27' => '2022-10-27',
    '2022-10-28' => '2022-10-28',
    '2022-10-29' => '2022-10-29'
];

$second = [
    '2022-10-24' => [
        'id' => 11,
        'user_id' => 1,
        'notitie' => 'Mag al helemaal niet',
        'datum' => '2022-10-24',
        'user_role' => 'client'
    ],
    '2022-10-26' => [
        'id' => 15,
        'user_id' => 1,
        'notitie' => 26,
        'datum' => '2022-10-26',
        'user_role' => 'client'
    ],
];

期望结果

Array
(
    [2022-10-23] => Array
        (
            [1] => 
        )

    [2022-10-24] => Array
        (
            [id] => 11
            [user_id] => 1
            [notitie] => Mag al helemaal niet 
            [datum] => 2022-10-24
            [user_role] => client
        )
    
    [2022-10-25] => Array
        (
            [1] => 
        )

    [2022-10-26] => Array
        (
            [id] => 15
            [user_id] => 1
            [notitie] => 26
            [datum] => 2022-10-26
            [user_role] => client
        )

    [2022-10-27] => Array
        (
            [1] => 
        )

    [2022-10-28] => Array
        (
            [1] => 
        )

    [2022-10-29] => Array
        (
            [1] => 
        )

)

尝试代码

if ($agendaButtonInfo == "timeGridWeek"){
    $userNotities = array();
    $dagenTussen = array();

    $period = new DatePeriod(
        new DateTime($agendaDatumBegin),
        new DateInterval('P1D'),
        new DateTime($agendaDatumEinde)
    );

    foreach ($period as $key => $value) {
        $dagenTussen[$value->format('Y-m-d')] =  $value->format('Y-m-d');
    }

    $stmt = $pdo->query("SELECT notitie_client.id, notitie_client.user_id, notitie_client.notitie, notitie_client.datum, user.user_role
        FROM (notitie_client 
        INNER JOIN user ON notitie_client.user_id = user.id) 
        WHERE notitie_client.user_id='$userId' AND notitie_client.datum BETWEEN '$agendaDatumBegin' AND '$agendaDatumEinde'
        ORDER BY notitie_client.datum ASC;");
  
    if ($stmt->rowCount() > 0) {
        while ($row = $stmt->fetch()) {
            $userNotities[$row["datum"]] = array( "id" => $row["id"], "user_id" => $row["user_id"], "notitie" => $row["notitie"], "datum" => $row["datum"], "user_role" => $row["user_role"]);
        }
    }  
    echo "<pre>";
        print_r($dagenTussen);
        echo "<pre>";
            print_r($userNotities);
                $notatieDatum[] = array();
                foreach ($userNotities as $notatie){
                    $notatieDatum[] = $notatie["datum"];
                }
                print_r ($notatieDatum);

                $eindArray = array();
                foreach ($dagenTussen as $dag){
                    echo "<br>";
                    if (in_array($dag, $notatieDatum))
                    {
                        echo "Match found";
                        print_r ($userNotities);
                    }
                    else
                    {
                        echo "Match not found";
                    }
                }
            }

问题分析与优化方案

你的尝试代码存在几个问题:

  1. 构建$notatieDatum时初始添加了空数组,会导致in_array检查出现误判
  2. 匹配成功时仅输出整个$userNotities,未将对应数据赋值到结果数组
  3. 使用in_array遍历查找效率低,直接检查数组键的存在性更高效

优化后的代码

直接遍历基准日期数组的键,通过isset快速判断是否存在匹配数据:

if ($agendaButtonInfo == "timeGridWeek"){
    $userNotities = [];
    $dagenTussen = [];

    $period = new DatePeriod(
        new DateTime($agendaDatumBegin),
        new DateInterval('P1D'),
        new DateTime($agendaDatumEinde)
    );

    foreach ($period as $value) {
        $dateStr = $value->format('Y-m-d');
        $dagenTussen[$dateStr] = $dateStr;
    }

    // 使用预处理语句防止SQL注入
    $stmt = $pdo->prepare("SELECT notitie_client.id, notitie_client.user_id, notitie_client.notitie, notitie_client.datum, user.user_role
        FROM notitie_client 
        INNER JOIN user ON notitie_client.user_id = user.id
        WHERE notitie_client.user_id = ? AND notitie_client.datum BETWEEN ? AND ?
        ORDER BY notitie_client.datum ASC;");
    $stmt->execute([$userId, $agendaDatumBegin, $agendaDatumEinde]);
  
    while ($row = $stmt->fetch()) {
        $userNotities[$row["datum"]] = [
            "id" => $row["id"],
            "user_id" => $row["user_id"],
            "notitie" => $row["notitie"],
            "datum" => $row["datum"],
            "user_role" => $row["user_role"]
        ];
    }  

    $eindArray = [];
    // 遍历基准日期的每个键
    foreach ($dagenTussen as $dateKey => $_) {
        // 检查是否有匹配的记录
        if (isset($userNotities[$dateKey])) {
            $eindArray[$dateKey] = $userNotities[$dateKey];
        } else {
            // 未匹配则填充指定结构
            $eindArray[$dateKey] = [1 => ''];
        }
    }

    // 输出结果
    echo "<pre>";
    print_r($eindArray);
    echo "</pre>";
}

额外提示

  • 原SQL语句存在注入风险,必须使用预处理语句
  • isset($userNotities[$dateKey])的时间复杂度为O(1),比in_array的O(n)效率高很多

内容的提问来源于stack exchange,提问作者NoobyPhper

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.16 10:02:24