Я пытаюсь отформатировать свои собственные данные (которые в настоящее время просто отображаются в различных таблицах и блоках индикаторов KPI) в формате, требуемом графической структурой. По сути, я хочу, чтобы некоторые из моих значений стали данными X и Y для скрипта, генерирующего график.
Это желаемый результат (пример массива, который работает, создавая график/графические точки):
$dataPoints = array(
array("x"=> 1, "y"=> 41, label=> "18/07/19"),
array("x"=> 2, "y"=> 35, label=> "19/07/19"),
array("x"=> 3, "y"=> 50, label=> "20/07/19"),
array("x"=> 4, "y"=> 45, label=> "21/07/19"),
array("x"=> 5, "y"=> 52, label=> "22/07/19"),
array("x"=> 6, "y"=> 68, label=> "23/07/19")
);
У меня есть следующий код, который извлекает необходимую мне информацию:
//Build Graph Data Points
//
$daysmax=31;
$daycounter=0;
while($daysmax > $daycounter) {
$sql_get_day_total_events = "SELECT COUNT(*),date_sub(curdate(),INTERVAL $daycounter day) as date1 FROM tblticketlog
WHERE DATE(date) = date_sub(curdate(),INTERVAL $daycounter day)
AND ((action = 'New Support Ticket Opened')
OR (action LIKE 'Status changed to Pending%')
OR (action LIKE 'Status changed to In Progress%')
OR (action LIKE 'New Ticket Response made by%'))";
$get_day_total_events_result=mysqli_query($db,$sql_get_day_total_events);
if (mysqli_num_rows($get_day_total_events_result) > 0) {
while($row = $get_day_total_events_result->fetch_assoc()) {
$day_result_date=strtotime($row['date1']);
$day_result_value=$row['COUNT(*)'];
}
}
$sql_get_day_escs = "SELECT COUNT(*) FROM escalations
WHERE DATE(esc_at) = date_sub(curdate(), INTERVAL $daycounter day)
AND escalated = 1";
$get_day_escs_result=mysqli_query($db2,$sql_get_day_escs);
if (mysqli_num_rows($get_day_escs_result) > 0) {
while($row = $get_day_escs_result->fetch_assoc()) {
$day_escs_value=$row['COUNT(*)'];
}
}
$day_slas_met = $day_result_value - $day_escs_value;
$day_kpi_pcnt = round((($day_slas_met / $day_result_value) * 100),0);
$daycounter=$daycounter + 1;
}
Подводя итог, я извлекаю общее количество событий в день в течение 30 дней (скользящее) из $db, я извлекаю количество «событий эскалации» в день в течение 30 дней (скользящее) из $db2. И я также беру дату из запроса $db.
Для моего графика:
Икс = $daycounter (просто возрастающий числовой идентификатор для точки данных, начиная с 0 и заканчивая 30
Д = Процент KPI, который только что рассчитан с помощью простой математики в $day_kpi_pcnt
МЕТКА = объект даты в текстовом формате
Что я пытался сделать
Я инициализировал массив $datapoints перед своим циклом с помощью:
$datapoints = array();
Затем непосредственно перед строкой $daycounter+1 в нижней части цикла я попытался передать свои значения индексам в массиве:
$datapoints[x] = $daycounter;
$datapoints[label] = date("d-m-Y",$day_result_date);
$datapoints[y] = $day_kpi_pcnt;
Однако это просто заканчивается пустым графиком. Если я var_dump массива, я, кажется, получаю последнюю строку моих результатов в пустом массиве:
**Day: 30 -- 29-06-2019 - 6/6 - 100%**
array(3) { ["x"]=> int(30) ["label"]=> string(10) "29-06-2019" ["y"]=> float(100) }
Честно говоря, PHP-массивы и их использование, наверное, моя самая слабая тема. Я действительно борюсь с ними и был бы признателен за некоторые советы или даже некоторые основные советы о том, где я ошибся. Спасибо.
@PaulSpiegel, вы правы, согласно вашему принятому ответу ниже, я устанавливал каждый из 3 индексов на значения данных в этой итерации цикла с помощью «=», поэтому каждый раз перезаписывал все предыдущие данные в этом индексе. Ваш ответ ясен и верен и в настоящее время работает в коде. Спасибо.






Вам нужен массив массивов. Сначала создайте массив для всех ваших результатов (он у вас уже есть) и временный массив (это вне цикла).
$datapoints = $temp_datapoint = array();
Затем создайте временный массив с вашими данными, как вы это сделали (это внутри цикла):
$temp_datapoint['x'] = $daycounter;
$temp_datapoint['label'] = date("d-m-Y",$day_result_date);
$temp_datapoint['y'] = $day_kpi_pcnt;
Затем добавьте весь этот массив в массив точек данных внутри цикла:
$datapoints[] = $temp_datapoint;
Просто для полноты я попробовал это, и это тоже работает, однако принятый ответ более аккуратный (и, вероятно, более правильный). Спасибо за отзыв.
То, что вы делаете, вероятно, выглядит примерно так:
$datapoints = [];
while (...) {
...
$datapoints[x] = $daycounter;
$datapoints[label] = date("d-m-Y",$day_result_date);
$datapoints[y] = $day_kpi_pcnt;
...
}
Вы перезаписываете массив $datapoints на каждой итерации цикла новыми значениями строк. Таким образом, будут сохранены только значения из последней строки. Вместо этого вам нужно добавить строки в массив:
$datapoints = [];
while (...) {
...
$datapoints[] = [
'x' => $daycounter,
'label' => date("d-m-Y",$day_result_date),
'y' => $day_kpi_pcnt,
];
...
}
Это правильный ответ на вопрос, который вы задали, но как только он заработает, вы должны передать его Обзор кода для получения дополнительной помощи. Построение массива в цикле, вызов встроенных в php функций mysql из бизнес-кода и введение переменных в операторы if — все это красные флажки, говорящие о том, что должен быть лучший способ. (То же, что и SQL в виде строк в вашем бизнес-коде, но выделить его сложнее.)
@ShapeOfMatter Я полностью с тобой. Есть над чем работать. Слишком много для одного вопроса на SO.
Спасибо @PaulSpiegel, этот ответ сработал, хотя позже я обнаружил, что массив был обратным для графика, поэтому использовал array_reverse(), и теперь все хорошо. Ответ отмечен как принятый.
@ShapeOfMatter, честно говоря, я полностью согласен, у меня никогда не было формального обучения PHP и я никогда не работал с реальной командой разработчиков PHP. Этому всему я научился самостоятельно, работая над небольшими проектами. Я на 100% ценю и понимаю, что не очень хорошо знаю PHP. Кроме того, я чувствую, что CodeReview просто уничтожит меня, лол .. Стек достаточно жесток по отношению к нубам!
@ShapeOfMatter Я действительно сделал обзор кода и опубликовал большую часть своего рабочего кода. Получил некоторую обратную связь, и мне удалось сократить время обработки с 9+ секунд до 488 мс. Так что спасибо за наводку
«Затем прямо перед строкой $daycounter+1 в нижней части цикла я попытался передать свои значения в индексы в массиве» — Где вы это делаете в своем коде? Вероятно, вы снова и снова перезаписываете массив в цикле. Довольно распространенная ошибка.