欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  后端开发

PHP 多维数组问题,有点难度!

程序员文章站 2022-05-01 11:31:20
...
这样两个数组:
//注册信息$array1 = array(0=>array('day'=>'2014-3-7',//注册日期'data'=>array(0=>array('uid'=>'0000001'),1=>array('uid'=>'0000002'),3=>array('uid'=>'0000003'),4=>array('uid'=>'0000004'),)),1=>array('day'=>'2014-3-8',//注册日期'data'=>array(0=>array('uid'=>'0000005'),1=>array('uid'=>'0000007'),2=>array('uid'=>'0000006'),)),2=>array('day'=>'2014-3-10',//注册日期'data'=>array(0=>array('uid'=>'0000008'),1=>array('uid'=>'0000010'),2=>array('uid'=>'0000009'),3=>array('uid'=>'0000012'),4=>array('uid'=>'0000013'),)),3=>array('day'=>'2014-3-11',//注册日期'data'=>array(0=>array('uid'=>'0000015'),1=>array('uid'=>'0000014'),2=>array('uid'=>'0000025'),3=>array('uid'=>'0000017'),4=>array('uid'=>'0000018'),)),);//登录日志$array2 = array(0=>array('day'=>'2014-3-8',//登录日期'ge_data'=>array(0=>array('uid'=>'0000001'),1=>array('uid'=>'0000002'),3=>array('uid'=>'0000003'))),1=>array('day'=>'2014-3-9',//登录日期'ge_data'=>array(0=>array('uid'=>'0000002'),1=>array('uid'=>'0000007'),2=>array('uid'=>'0000006'),)),2=>array('day'=>'2014-3-11',//登录日期'ge_data'=>array(0=>array('uid'=>'0000001'),1=>array('uid'=>'0000007'),2=>array('uid'=>'0000008'),3=>array('uid'=>'0000012'),4=>array('uid'=>'0000013'),5=>array('uid'=>'0000003'),6=>array('uid'=>'0000002'))));


如何能得到以下数组:


各位帮帮忙!


回复讨论(解决方案)

确实很难。。。

用纯属组不是不能做

但是代码太有针对性 用过一次以后未必好用

建议这种东西存入数据库 然后就任意揉捏了.

看你的数组和需求不是很明朗

用纯属组不是不能做

但是代码太有针对性 用过一次以后未必好用

建议这种东西存入数据库 然后就任意揉捏了. 这就是从数据库读出来的

看你的数组和需求不是很明朗 实际上就是计算一个次日留存数。比如 3月7日注册了4个人,查询3月8日有哪几个人登录过。

2014-03-09第3天登录人数为啥是0 不应该是11号吗?那天有7个人登录啊

2014-03-09第3天登录人数为啥是0 不应该是11号吗?那天有7个人登录啊 因为3月9号注册人数为零。所以在3月9号的第N天登录人数都是0


2014-03-09第3天登录人数为啥是0 不应该是11号吗?那天有7个人登录啊 因为3月9号注册人数为零。所以在3月9号的第N天登录人数都是0
还有这逻辑 我表示我凌乱了



2014-03-09第3天登录人数为啥是0 不应该是11号吗?那天有7个人登录啊 因为3月9号注册人数为零。所以在3月9号的第N天登录人数都是0
还有这逻辑 我表示我凌乱了 3月9号注册人数为零,所以这一天的uid都为空,所以在登录日志表里是无论如何也找不到3月9号的次日留存数的。

查询当日注册的账号,在之后的第n(n是自然数)日当日,也登录的账号;
最终要实现的结果如下图:


不要沉贴啊!有哪位高手能帮帮忙啊!!!

不难 就是复杂 花时间... 今天又要加班.... 没时间弄啊

你可以多次循环来取值

先声明一个结果空数组

然后循环第一个数组,把日期保存进入

再循环第一个 第二个数组 依次判断想要的数据 加起来以后放进结果数组

不难 就是复杂 花时间... 今天又要加班.... 没时间弄啊

你可以多次循环来取值

先声明一个结果空数组

然后循环第一个数组,把日期保存进入

再循环第一个 第二个数组 依次判断想要的数据 加起来以后放进结果数组 哎,我自己试过写这个循环呢,可惜啊,写不出来!

不是类似乘法口诀嘛 看那图表

可以这样写

//注册信息$array1 = array(0=>array('day'=>'2014-3-7',//注册日期'data'=>array(0=>array('uid'=>'0000001'),1=>array('uid'=>'0000002'),3=>array('uid'=>'0000003'),4=>array('uid'=>'0000004'),)),1=>array('day'=>'2014-3-8',//注册日期'data'=>array(0=>array('uid'=>'0000005'),1=>array('uid'=>'0000007'),2=>array('uid'=>'0000006'),)),2=>array('day'=>'2014-3-10',//注册日期'data'=>array(0=>array('uid'=>'0000008'),1=>array('uid'=>'0000010'),2=>array('uid'=>'0000009'),3=>array('uid'=>'0000012'),4=>array('uid'=>'0000013'),)),3=>array('day'=>'2014-3-11',//注册日期'data'=>array(0=>array('uid'=>'0000015'),1=>array('uid'=>'0000014'),2=>array('uid'=>'0000025'),3=>array('uid'=>'0000017'),4=>array('uid'=>'0000018'),)),); //登录日志$array2 = array(0=>array('day'=>'2014-3-8',//登录日期'ge_data'=>array(0=>array('uid'=>'0000001'),1=>array('uid'=>'0000002'),3=>array('uid'=>'0000003'))),1=>array('day'=>'2014-3-9',//登录日期'ge_data'=>array(0=>array('uid'=>'0000002'),1=>array('uid'=>'0000007'),2=>array('uid'=>'0000006'),)),2=>array('day'=>'2014-3-11',//登录日期'ge_data'=>array(0=>array('uid'=>'0000001'),1=>array('uid'=>'0000007'),2=>array('uid'=>'0000008'),3=>array('uid'=>'0000012'),4=>array('uid'=>'0000013'),5=>array('uid'=>'0000003'),6=>array('uid'=>'0000002'))));$res = array();//读取每天的注册记录foreach($array1 as $r) {  $day = $r['day'];  $res[$day] = array('day' => $day, 'count' => count($r['data']));  $d = date('z', strtotime($day));  //对于当日注册每个用户  foreach($r['data'] as $us) {    foreach($array2 as $t) {      $rd = date('z', strtotime($t['day']));      //检查他在哪天登录了      foreach($t['ge_data'] as $u) {        if($us['uid'] == $u['uid']) $res[$day]['day_'.($rd-$d)][] = $us['uid']; //保存登录的uid以便于检查      }    }  }}print_r($res);
Array(    [2014-3-7] => Array        (            [day] => 2014-3-7            [count] => 4            [day_1] => Array                (                    [0] => 0000001                    [1] => 0000002                    [2] => 0000003                )            [day_4] => Array                (                    [0] => 0000001                    [1] => 0000002                    [2] => 0000003                )            [day_2] => Array                (                    [0] => 0000002                )        )    [2014-3-8] => Array        (            [day] => 2014-3-8            [count] => 3            [day_1] => Array                (                    [0] => 0000007                    [1] => 0000006                )            [day_3] => Array                (                    [0] => 0000007                )        )    [2014-3-10] => Array        (            [day] => 2014-3-10            [count] => 5            [day_1] => Array                (                    [0] => 0000008                    [1] => 0000012                    [2] => 0000013                )        )    [2014-3-11] => Array        (            [day] => 2014-3-11            [count] => 5        ))

遗憾的是根据你的数据,不能得到你示例的结果
应该是你弄错了

不是类似乘法口诀嘛 看那图表 哈哈,是有点像。
我这个功能是这样的,那个起始是起始日期,比如2014-1-1,结束是结束日期,比如2014-1-6,查询出来2014-1-1至2014-1-6的留存数目,看第一行,1-1新增100人,+1就表示1-2登录有多少人,+2就表示1-3登录有多少人。哎,这功能是运营提出来的,着实让我头疼啊这是!!!

可以这样写

//注册信息$array1 = array(0=>array('day'=>'2014-3-7',//注册日期'data'=>array(0=>array('uid'=>'0000001'),1=>array('uid'=>'0000002'),3=>array('uid'=>'0000003'),4=>array('uid'=>'0000004'),)),1=>array('day'=>'2014-3-8',//注册日期'data'=>array(0=>array('uid'=>'0000005'),1=>array('uid'=>'0000007'),2=>array('uid'=>'0000006'),)),2=>array('day'=>'2014-3-10',//注册日期'data'=>array(0=>array('uid'=>'0000008'),1=>array('uid'=>'0000010'),2=>array('uid'=>'0000009'),3=>array('uid'=>'0000012'),4=>array('uid'=>'0000013'),)),3=>array('day'=>'2014-3-11',//注册日期'data'=>array(0=>array('uid'=>'0000015'),1=>array('uid'=>'0000014'),2=>array('uid'=>'0000025'),3=>array('uid'=>'0000017'),4=>array('uid'=>'0000018'),)),); //登录日志$array2 = array(0=>array('day'=>'2014-3-8',//登录日期'ge_data'=>array(0=>array('uid'=>'0000001'),1=>array('uid'=>'0000002'),3=>array('uid'=>'0000003'))),1=>array('day'=>'2014-3-9',//登录日期'ge_data'=>array(0=>array('uid'=>'0000002'),1=>array('uid'=>'0000007'),2=>array('uid'=>'0000006'),)),2=>array('day'=>'2014-3-11',//登录日期'ge_data'=>array(0=>array('uid'=>'0000001'),1=>array('uid'=>'0000007'),2=>array('uid'=>'0000008'),3=>array('uid'=>'0000012'),4=>array('uid'=>'0000013'),5=>array('uid'=>'0000003'),6=>array('uid'=>'0000002'))));$res = array();//读取每天的注册记录foreach($array1 as $r) {  $day = $r['day'];  $res[$day] = array('day' => $day, 'count' => count($r['data']));  $d = date('z', strtotime($day));  //对于当日注册每个用户  foreach($r['data'] as $us) {    foreach($array2 as $t) {      $rd = date('z', strtotime($t['day']));      //检查他在哪天登录了      foreach($t['ge_data'] as $u) {        if($us['uid'] == $u['uid']) $res[$day]['day_'.($rd-$d)][] = $us['uid']; //保存登录的uid以便于检查      }    }  }}print_r($res);
Array(    [2014-3-7] => Array        (            [day] => 2014-3-7            [count] => 4            [day_1] => Array                (                    [0] => 0000001                    [1] => 0000002                    [2] => 0000003                )            [day_4] => Array                (                    [0] => 0000001                    [1] => 0000002                    [2] => 0000003                )            [day_2] => Array                (                    [0] => 0000002                )        )    [2014-3-8] => Array        (            [day] => 2014-3-8            [count] => 3            [day_1] => Array                (                    [0] => 0000007                    [1] => 0000006                )            [day_3] => Array                (                    [0] => 0000007                )        )    [2014-3-10] => Array        (            [day] => 2014-3-10            [count] => 5            [day_1] => Array                (                    [0] => 0000008                    [1] => 0000012                    [2] => 0000013                )        )    [2014-3-11] => Array        (            [day] => 2014-3-11            [count] => 5        ))

遗憾的是根据你的数据,不能得到你示例的结果
应该是你弄错了 非常感谢!我看看!参考一下!看看能不能得到我想要的结果!

既然是从数据库读出来的。。我觉得还是改进下sql语句好一点。。你查完了再修改数组有点舍近求远

既然是从数据库读出来的。。我觉得还是改进下sql语句好一点。。你查完了再修改数组有点舍近求远 这个是从mongodb数据集里读出来的!要是mysql还好呢!我就不用这么费劲了!

我来观摩下看看 大家是怎么分析此类问题的

涨姿势啦!都是大神

大神们!还有没有别的招儿了?我现在已经焦头烂额了在这!

看了半天有点晕, 不知道你这数组里的内容是随便写的还是真实数据,如果是真实数据 我怎么算都算不出来你这个数儿呢, 除了 第二天的对.
如果你的登录人数就是登录人数的话, 第三天的怎么会是1 ?
你这个登录人数 = 登录日志里的人数, 还是说 登录人数 = 登录日志人数 + 注册人数. 先把问题表述清楚了.

看了半天有点晕, 不知道你这数组里的内容是随便写的还是真实数据,如果是真实数据 我怎么算都算不出来你这个数儿呢, 除了 第二天的对.
如果你的登录人数就是登录人数的话, 第三天的怎么会是1 ?
你这个登录人数 = 登录日志里的人数, 还是说 登录人数 = 登录日志人数 + 注册人数. 先把问题表述清楚了.
3月7日里注册的UID有:0000001,0000002,0000003,0000004
3月8日登录的UID有:0000001,0000002,0000003
3月9日登录的UID有:0000002,0000006,0000007
所以针对3月7日,他的第二天也就是3月9日登录的UID只有一个0000002
以下都依次类推。。。


看了半天有点晕, 不知道你这数组里的内容是随便写的还是真实数据,如果是真实数据 我怎么算都算不出来你这个数儿呢, 除了 第二天的对.
如果你的登录人数就是登录人数的话, 第三天的怎么会是1 ?
你这个登录人数 = 登录日志里的人数, 还是说 登录人数 = 登录日志人数 + 注册人数. 先把问题表述清楚了.
3月7日里注册的UID有:0000001,0000002,0000003,0000004
3月8日登录的UID有:0000001,0000002,0000003
3月9日登录的UID有:0000002,0000006,0000007
所以针对3月7日,他的第二天也就是3月9日登录的UID只有一个0000002
以下都依次类推。。。 写错了,是第三天也就是3月9日

所以应该是

    [2014-3-7] => Array        (            [day] => 2014-3-7            [count] => 4            [day_1] => Array                (                    [0] => 0000001                    [1] => 0000002                    [2] => 0000003                )             [day_4] => Array                (                    [0] => 0000001                    [1] => 0000002                    [2] => 0000003                )             [day_2] => Array                (                    [0] => 0000002                )         )


第二天 3 个
第三天 1 个
第五天 3 个
而绝没有第四天的2 个!

照你这么说那也不对啊3月8日第4天的登录人数为啥为1 不应该是2吗?

照你这么说那也不对啊3月8日第4天的登录人数为啥为1 不应该是2吗?
哦看错了

所以应该是

    [2014-3-7] => Array        (            [day] => 2014-3-7            [count] => 4            [day_1] => Array                (                    [0] => 0000001                    [1] => 0000002                    [2] => 0000003                )             [day_4] => Array                (                    [0] => 0000001                    [1] => 0000002                    [2] => 0000003                )             [day_2] => Array                (                    [0] => 0000002                )         )


第二天 3 个
第三天 1 个
第五天 3 个
而绝没有第四天的2 个! 嗯,我这块写错了。

正确的算法,不会得到错误的结果
基本算法我 #15 已经给了,你的工作只是优化一下

正确的算法,不会得到错误的结果
基本算法我 #15 已经给了,你的工作只是优化一下 我在想,把你那个数组,再处理一下变成我要的数组。

$array = array(    '2014-3-7' => array(        'day' => '2014-3-7',        'count' => 4,        'day_1' => array(            0 => 0000001,            1 => 0000002,            2 => 0000003        ) ,        'day_4' => array(            0 => 0000001,            1 => 0000002,            2 => 0000003        ) ,        'day_3' => array(            0 => 0000001,            1 => 0000002        ) ,        'day_2' => array(            0 => 0000002        ) ,        'day_5' => array(            0 => 0000002        )    ) ,    '2014-3-8' => array(        'day' => '2014-3-8',        'count' => 3,        'day_4' => array(            0 => 0000005,            1 => 0000007        ) ,        'day_2' => array(            0 => 0000005,            1 => 0000007,            2 => 0000006        ) ,        'day_1' => array(            0 => 0000007,            1 => 0000006        ) ,        'day_3' => array(            0 => 0000007,            1 => 0000006        )    ) ,    '2014-3-10' => array(        'day' => '2014-3-10',        'count' => 5,        'day_1' => array(            0 => 0000008,            1 => 0000012,            2 => 0000013        ) ,        'day_2' => array(            0 => 0000008,            1 => 0000010,            2 => 0000012,            3 => 0000013        )    ) ,    '2014-3-11' => array(        'day' => '2014-3-11',        'count' => 5,        'day_1' => array(            0 => 0000015,            1 => 0000025,            2 => 0000018        )    ));

这有什么可想的?
$res[$day]['day_'.($rd-$d)][] = $us['uid'];
改成
$res[$day]['day_'.($rd-$d)]++;
不就是计数了吗?

这有什么可想的?
$res[$day]['day_'.($rd-$d)][] = $us['uid'];
改成
$res[$day]['day_'.($rd-$d)]++;
不就是计数了吗?

$d = date('z', strtotime($day));这个是什么意思?

$d = date('z', strtotime($day));
中:
$day 是数组提供的 日期串
strtotime($day) 将日期串转换为unix时间戳
date('z', strtotime($day)) 取得日期是在一年中的第几天

哎!跟我想要的最终结果还是有些不一样啊!

$d = date('z', strtotime($day));
中:
$day 是数组提供的 日期串
strtotime($day) 将日期串转换为unix时间戳
date('z', strtotime($day)) 取得日期是在一年中的第几天 为什么我换一组数据,会出现:[day_0] => Array
(
[0] => 3001000
[1] => 3001726
[2] => 3001728
[3] => 3001733
[4] => 3001734
[5] => 3001735
[6] => 3001745
)这个是怎么回事?

注册信息($array1)和登录信息($array2)时间(day)相同时,就会出现 day_0

注册信息($array1)和登录信息($array2)时间(day)相同时,就会出现 day_0 怎样避免呢?在哪能加个判断?

要避免干什么?当天注册,当天登录,不是很正常吗?

要避免干什么?当天注册,当天登录,不是很正常吗?

要避免干什么?当天注册,当天登录,不是很正常吗? 可我就想计算他第N天登录的啊!


要避免干什么?当天注册,当天登录,不是很正常吗?

要避免干什么?当天注册,当天登录,不是很正常吗? 可我就想计算他第N天登录的啊! 哦了,知道了,我不取就得了。