简体   繁体   English

PHP按日期从数组中获取不同的ID数

[英]PHP get distinct ids count from an array by date

Looking for the simplest way to achieve the following in php:寻找在php中实现以下内容的最简单方法:

I have this array with dates and ids我有这个带有日期和 ID 的数组

$data = array(
  array("date" => "2016-01", "ids" => array(1,2,3,4,5,6,7,8)),
  array("date" => "2016-02", "ids" => array(1,2,9,10,11,12)),
  array("date" => "2016-03", "ids" => array(3,16,17,18,19,20,21)),
  array("date" => "2016-04", "ids" => array(1,2,3,19,20,22,23))
);

The idea is to count ids by date but also return count(existing ids) since the start of every month separately.这个想法是按日期计算 id,但也从每个月的开始分别返回计数(现有 id)。 (I hope this is understandable) (我希望这是可以理解的)

The returned array should look like this:返回的数组应如下所示:

$data = array(
  array("date" => "2016-01", "counter" => array(8)),
  array("date" => "2016-02", "counter" => array(2,4)), /* 2 existing ids from 2016-01 and 4 new in 2016-02) */
  array("date" => "2016-03", "counter" => array(1,0,6)), /* 1 existing from 2016-01 and 0 exiting from 2016-02 and 6 new */
  array("date" => "2016-04", "counter" => array(3,0,2,2)) /* etc. */
);



        | 2016-01 | 2016-02 | 2016-03 | 2016-04
------  | ------- | ------- | ------- | -------
2016-01 |     8   |         |         |         
------  | ------- | ------- | ------- | -------
2016-02 |     2   |    4    |         |        
------  | ------- | ------- | ------- | -------
2016-03 |     1   |    0    |    6    |        
------  | ------- | ------- | ------- | -------
2016-04 |     3   |    0    |    2    |    2   

Of course if there is a way to do that directly in sql i'll take it :)当然,如果有办法直接在 sql 中做到这一点,我会接受:)

Here is one way to do it.这是一种方法。 (I'm not sure if it's the simplest). (我不确定它是否是最简单的)。 Looping over the set of data is the easiest part.循环数据集是最简单的部分。

Within that, consider each id from the current day with while ($id = array_pop($day['ids'])) .其中,使用while ($id = array_pop($day['ids']))考虑当天的每个 id。 For each of those ids, start at the first day, and look for the id in that days set of ids.对于这些 id 中的每一个,从第一天开始,并在当天的 id 集中查找该 id。 If it's found, increment the count for that day and continue with the next id ( continue 2 continues the while loop.) If it's not found, move on to the next day.如果找到,则增加当天的计数并继续下一个 id( continue 2继续while循环。)如果未找到,则继续到第二天。 If it's not found when you get to the current day (indicated by $i < $key in the for loop) then increment the count for the current day and move on to the next id.如果在您到达当天时未找到(在for循环中由$i < $key表示),则增加当天的计数并移至下一个 id。

foreach ($data as $key => $day) {
    $counts = array_fill(0, $key + 1, 0);
    while ($id = array_pop($day['ids'])) {
        for ($i=0; $i < $key; $i++) {
            $past_day = $data[$i];
            if (in_array($id, $past_day['ids'])) {
                $counts[$i]++;
                continue 2;
            }
        }
        $counts[$key]++;
    }
    $new_data[] = ['date' => $day['date'], 'counter' => $counts];
}

ps I have no idea how to do this in SQL. ps 我不知道如何在 SQL 中做到这一点。

You can do something like this to achieve the desired result,你可以做这样的事情来达到预期的结果,

$newArray = array();
$count = count($data);
for($i = 0; $i < $count; ++$i){
    $newArray[$i] = array('date' => $data[$i]['date'], 'counter' => array());
    for($j = 0; $j < $i; ++$j){
        $counter = 0;
        foreach($data[$i]['ids'] as $key => $id){
            if(in_array($id, $data[$j]['ids'])){
                ++$counter;
                unset($data[$i]['ids'][$key]);
            }
        }
        $newArray[$i]['counter'][] = $counter;
    }
    $newArray[$i]['counter'][] = count($data[$i]['ids']);
}

// display $newArray array
var_dump($newArray);

Here's the live demo这是现场演示

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM