i have a loop where i am getting items from database, currently there are 314 ids in my array and i get the items like so.
$s_standards = [];
$s_sub_category = [];
foreach ($sanitized_needs['standard'] as $skey => $standard) {
$sname = DB::table('lesson_observation_teacher_standards')->where('id', $standard)->first()->name;
$s_standards[] = $sname;
foreach ($sanitized_needs['sub_category'] as $key => $substandard) {
$name = DB::table('lesson_observation_teacher_standard_categories')->where('id', $substandard)->first()->name;
if ($key == $skey) {
$s_sub_category[$sname][] = $name;
}
}
}
I know i could use WhereIn but i need the duplicates to calculate the categories.
Both $santized_needs['standard'] and $santized_needs['sub_category'] have 314 ids. But when this runs it throws 500 internal server error but when i comment the queries out and replace them with string it works. My guess is the database is restricting mass queries. There's no error message in both laravel.log and network tab in browser.
Is there any way i can disable the restrictions put on database or laravel?
UPDATE: Here are some samples of $sanitized_needs array.
array:2 [
"standard" => array:312 [
0 => "C216114B-8751-3874-9154-FC22679569E0"
1 => "871E5F62-0E1B-3338-969C-2DC4604C8722"
2 => "B0161059-E9F6-376E-8BB1-B4BF1B10C30F"
3 => "D1380FB6-37A8-3B3B-B877-A5AF21D9385F"
4 => "D1380FB6-37A8-3B3B-B877-A5AF21D9385F"
5 => "676038A6-13D0-32CC-BAD7-A7DA9CFB28EA"
6 => "D1380FB6-37A8-3B3B-B877-A5AF21D9385F"
7 => "C216114B-8751-3874-9154-FC22679569E0"
8 => "676038A6-13D0-32CC-BAD7-A7DA9CFB28EA"
9 => "676038A6-13D0-32CC-BAD7-A7DA9CFB28EA"
10 => "C216114B-8751-3874-9154-FC22679569E0"
...
]
"sub_category" => array:312 [
0 => "B2A688A3-1C72-31F4-91CD-6891B5A1D512"
1 => "5E896BF5-2A99-3059-900A-E1BBBDABF20D"
2 => "050582A4-003B-3034-A401-040D51A8A751"
3 => "63ACE688-9F88-3C63-9556-2A291A9C7651"
4 => "4B8D400E-8160-3D1C-A846-33BA8E93AFB3"
5 => "7AEE6E97-2F84-3EAA-BC8D-409C6DD48CA3"
6 => "4B8D400E-8160-3D1C-A846-33BA8E93AFB3"
7 => "5A878A27-85FC-3FC5-B8FA-70AB7A35D1EB"
8 => "7AEE6E97-2F84-3EAA-BC8D-409C6DD48CA3"
9 => "7AEE6E97-2F84-3EAA-BC8D-409C6DD48CA3"
10 => "596547E6-F3CD-3732-913B-68862898F16C"
...
]
]
Tried everything i could ended up changing this part of the code like so
$s_standards = [];
$s_sub_category = [];
$all_subs = DB::table('lesson_observation_teacher_standard_categories')->pluck('name','id')->toArray();
foreach ($sanitized_needs['standard'] as $skey => $standard) {
$sname = DB::table('lesson_observation_teacher_standards')->where('id', $standard)->first()->name;
$s_standards[] = $sname;
foreach ($sanitized_needs['sub_category'] as $key => $substandard) {
$name = $all_subs[$substandard];
if ($key == $skey) {
$s_sub_category[$sname][] = $name;
}
}
}
Now i am just preloading the categories and searching them in array.
Now it works fine
Related
This question already has an answer here:
How to extract and access data from JSON with PHP?
(1 answer)
Closed 1 year ago.
I have a DB column with a string as shown below
{"gpslev":"11","gsmlev":"4","hdop":"0.4","io16":"202847595","io175":"-1","io200":"0","io236":"0","io239":"0","io240":"0","io241":"65510","io247":"0","io251":"0","io252":"0","io253":"0","io254":"25","io310":"0","io66":"12299","io67":"4014","io68":"0","io69":"1","pdop":"0.5"}
I want to extract certain data from this string and echo it to a PHP page
I have used the following to no avail
function populateArrayFromString($string)
{
$array = [];
$pairs = explode(",", $string);
foreach ($pairs as $pair) {
list($key, $value) = explode(":", $pair);
$arrayToReturn[trim($key, '"')] = trim($value, '"');
}
return $array;
}
$result = mysql_query("SELECT * FROM gs_objects WHERE imei = '354018115539821' ");
?>
<?php
while ($row = mysql_fetch_array($result)) {
$data = populateArrayFromString($row['params']);
?>
<?php echo $row['params']; ?>
</br>
<?php echo $data['io16']; ?>
If I echo the PARAMS coumn I see the whole string. If I echo the io16 in the param colum I get error
Notice: Undefined index: io16
use
$stmt = '{"gpslev":"11","gsmlev":"4","hdop":"0.4","io16":"202847595","io175":"-1","io200":"0","io236":"0","io239":"0","io240":"0","io241":"65510","io247":"0","io251":"0","io252":"0","io253":"0","io254":"25","io310":"0","io66":"12299","io67":"4014","io68":"0","io69":"1","pdop":"0.5"}';
$result = json_decode($stmt,true);
print_r($result);
and you will get and array
Array
(
[gpslev] => 11
[gsmlev] => 4
[hdop] => 0.4
[io16] => 202847595
[io175] => -1
[io200] => 0
[io236] => 0
[io239] => 0
[io240] => 0
[io241] => 65510
[io247] => 0
[io251] => 0
[io252] => 0
[io253] => 0
[io254] => 25
[io310] => 0
[io66] => 12299
[io67] => 4014
[io68] => 0
[io69] => 1
[pdop] => 0.5
)
No nbeed to self poarse the json
Could someone please assist in achieving that follow tasks please?
How to create a CSV export from a multidimensional array, but to have dynamic grouped column headings
Array (
[0] => Array ( [months] => 06/2020 [hours] => 202 [skill] => 5 )
[1] => Array ( [months] => 06/2020 [hours] => 563.5 [skill] => 6 )
[2] => Array ( [months] => 07/2020 [hours] => 140.5 [skill] => 6 )
[3] => Array ( [months] => 07/2020 [hours] => 522.5 [skill] => 5 )
)
So the output on the CSV would be like
+----------------------------+------------+--------+
| | Skill 6 |Skill 5 |
+----------------------------+------------+--------+
| 06/2020 | 563.5 | 202 |
+----------------------------+------------+--------+
| 07/2020 | 140.5 | 522.5 |
+----------------------------+------------+--------+
Added CSV output I have so far
Current CSV Element of the code
header("Content-type: text/csv");
header("Content-Disposition: attachment; filename=result_file.csv");
header("Pragma: no-cache");
header("Expires: 0");
// Building $data_array from DB
foreach ($data_array as $subarray) {
$tempKey = $subarray['skill'].$subarray['months'];
$subarray['hours'] = str_replace(',', '', $subarray['hours']);
if (isset($result[$tempKey])) {
$result[$tempKey]['hours'] += $subarray['hours'];
} else {
$result[$tempKey] = $subarray;
}
}
// CSV Output
outputCSV($result);
function outputCSV($result) {
$output = fopen("php://output", "w");
foreach ($result as $row) {
fputcsv($output, $row);
}
fclose($output);
}
any help would be greatly appreciated, TIA
Question edited
Pretty sure if I thought about this for a bit I could improve it but it seems like it gets the right answer
$in = [
[ 'months' => '06/2020', 'hours' => 202, 'skill' => 5 ],
[ 'months' => '06/2020', 'hours' => 563.5, 'skill' => 6 ],
[ 'months' => '07/2020', 'hours' => 140.5, 'skill' => 6 ],
[ 'months' => '07/2020', 'hours' => 522.5, 'skill' => 5 ]
];
$firstTitle = 'Month';
$months = [];
$skills = [$firstTitle=>1];
// make an array keyed on the date
foreach ( $in as $t) {
$months[$t['months']]['skill'.$t['skill']] = $t['hours'];
$skills['skill'.$t['skill']] = 1;
}
// sort skills into assending order
ksort($skills);
// open a file
$xl = fopen('excelfile.csv', 'w');
// echo title line from the skills array
fputcsv($xl, array_keys($skills));
// build csv line with skills in the correct order
foreach ($months as $date => $m){
// build array in correct sorted order
$t = [];
$t[] = $date;
foreach ($skills as $skill => $x) {
if ( $skill != $firstTitle) $t[] = $m[$skill];
}
fputcsv($xl,$t);
}
RESULT
Month,skill5,skill6
06/2020,202,563.5
07/2020,522.5,140.5
You're basically just aggregating the skill values by month and then outputting those aggregated values. This is not difficult, but you've got to be clear about what you're doing. One common reason I see new players get confused is that they're trying to use the most compact code possible, which makes it hard to keep track of what's happening. Be verbose, name things clearly, and comment your code relentlessly. You'll have a much easier time seeing why something isn't working, and your code will be much more maintainable. Write your code like someone else is going to be maintaining it. That someone else may be you in five years.
<?php
$dataArray = [
['months' => '06/2020', 'hours' => '202', 'skill' => '5'],
['months' => '06/2020', 'hours' => '563.5', 'skill' => '6'],
['months' => '06/2020', 'hours' => '303.7', 'skill' => '6'],
['months' => '08/2020', 'hours' => '123.5', 'skill' => '8'],
['months' => '07/2020', 'hours' => '140.5', 'skill' => '6'],
['months' => '07/2020', 'hours' => '522.5', 'skill' => '5'],
['months' => '08/2020', 'hours' => '123.5', 'skill' => '6']
];
/*
* Break out your formatting into functions so that it's re-usable and doesn't clutter up your logic
*/
function formatHours($hourString)
{
$hourString = str_replace(',', '', $hourString);
return floatval($hourString);
}
function buildSkillKey($skillValue)
{
return 'Skill '.$skillValue;
}
// Set up buffers for our skills and month values
$skills = [];
$buffer = [];
foreach($dataArray as $currRow)
{
//Format the hour value
$currHours = formatHours($currRow['hours']);
//Create key for the skill.
$skillKey = buildSkillKey($currRow['skill']);
/*
* Add the skill to the skill buffer. Using the value as the key is an easy way to both prevent duplicates
* without having to implement any logic, and have automatic alpha sorting
*/
$skills[$skillKey] = $skillKey;
// Set up an array for the month value if we don't have one already
if(!array_key_exists($currRow['months'], $buffer))
{
$buffer[$currRow['months']] = [];
}
/*
* If you don't have multiple month/skill entries that you need to aggregate, remove this condition
* and simply set the value in the buffer rather than adding with +=
*/
if(!array_key_exists($skillKey, $buffer[$currRow['months']]))
{
$buffer[$currRow['months']][$skillKey] = 0;
}
$buffer[$currRow['months']][$skillKey] += $currHours;
}
// Define a string for the months column header
$monthColumnTitle = '';
// Create the header row by combining the month header and the skills buffer
$header = array_merge([$monthColumnTitle], $skills);
// Open an output handle and send the header
$outputHandle = fopen("skills.csv", "w");
fputcsv($outputHandle, $header);
// Spin through the buffer
foreach($buffer as $currMonth=>$currSkillValues)
{
// Initialize an output array with the month in the first position
$currOutput = [$currMonth];
// Iterate through the skill buffer
foreach($skills as $currSkillLabel)
{
/*
* If we have a value for this skill, add it to the output row, otherwise insert an empty string.
*
* If you prefer to send zeros rather than empty strings, you can just set the field value to
* $currSkillValues[$currSkillLabel], since we initialized all skills with zeroes when building
* the value buffer.
*/
$currFieldValue = (!empty($currSkillValues[$currSkillLabel])) ? $currSkillValues[$currSkillLabel]:'';
$currOutput[] = $currFieldValue;
}
// Send the row
fputcsv($outputHandle, $currOutput);
}
Following is my PHP code:
while($row = $resp->fetch_assoc())
{
$itemArray = array(
array(
'name' => $row["product_name"],
'id' => $row["id"],
'image' => $row['images'],
'discount' => $row["discount"],
'quantity' => $min_quantity,
'price' => $row["price"]
)
);
}
if(!empty($_SESSION["cart_item"]))
{
if(in_array($itemArray, $_SESSION["cart_item"]))
{
foreach($_SESSION["cart_item"] as $item)
{
if(in_array($item, $itemArray))
$_SESSION["cart_item"][$item]["quantity"] = $min_quantity;
break;
}
}
else
{
$_SESSION["cart_item"] = array_merge($_SESSION["cart_item"],$itemArray);
}
}
else
{
$_SESSION["cart_item"] = $itemArray;
}
After executing this code i am getting a response like this:
Array
(
[0] => Array
(
[name] => Girls Designer Dress
[id] => 4
[image] => s:146:"2017/march/meetfashion01-04-2017_12-19-07_am.jpg,2017/march/meetfashion01-04-2017_12-19-08_am
.jpg,2017/march/meetfashion01-04-2017_12-19-09_am.jpg";
[discount] => 10
[quantity] => 1
[price] => 1200
)
)
What I am trying to acheive is if user adds the same product in cart whose data we have got in response then instead of creating once more array and merging it one after another i want to just update the quantity of the same product from 1 to 2.
I am stuck in this part of code
foreach($_SESSION["cart_item"] as $item)
{
if(in_array($item, $itemArray))
$_SESSION["cart_item"][$item]["quantity"] = $min_quantity;
break;
}
I have tried it many times that if same product is encountered then increment the quantity by 1 for the same product and don't create one more array.
Can anyone help with this logic and code?
is $_SESSION["cart-item"] a single Array like?
Array
(
[name] => Girls Designer Dress
[id] => 4
[image] => s:146:"2017/march/meetfashion01-04-2017_12-19-07_am.jpg,2017/march/meetfashion01-04-2017_12-19-08_am
.jpg,2017/march/meetfashion01-04-2017_12-19-09_am.jpg";
[discount] => 10
[quantity] => 1
[price] => 1200
)
If so then don't call a foreach instead just check directly if that cart-item is in the $itemArray using array_search().
(The function search in a array and if needle is found return its index else return false).
$cartItemPosition = array_search($_SESSION['cart-item'], $itemArray);
if($cartItemPosition == false) {
// Not found in array, so create new entry
$itemArray.push($_SESSION['cart-item']);
}else {
// Found in array so edit existing entry
$itemArray[$cartItemPosition]['quantity'] = 999;
}
The below works if $itemArray has only 1 item :
Change to :
if(!empty($_SESSION["cart_item"]))
{
if(in_array($itemArray[0], $_SESSION["cart_item"]))
{
foreach($_SESSION["cart_item"] as $index => $item)
{
if(in_array($item, $itemArray))
$_SESSION["cart_item"][$index]["quantity"] = $_SESSION["cart_item"][$index]["quantity"] + 1;
break;
}
}
else
{
$_SESSION["cart_item"] = array_merge($_SESSION["cart_item"],$itemArray);
}
}
else
{
$_SESSION["cart_item"] = $itemArray;
}
Added [0] in first if statement of in_array.
Added $index in the foreach loop and used it.
Your code before never went to the if statement. If $itemArray is always containing an array inside an array (that's why we used [0]) then it should be like that.
If it is possible that $itemArray has more than 1 items then we will have to edit the answer as needed.
Also not sure, but if your fetching loop is possible to return more than one items then it's wrong becuse you will only have the last result. If you know that you will only have 1 result back then it's all good.
while($row = $resp->fetch_assoc())
{
$itemArray = array(
array(
'name' => $row["product_name"],
'id' => $row["id"],
'image' => $row['images'],
'discount' => $row["discount"],
'quantity' => $min_quantity,
'price' => $row["price"]
)
);
}
I'm trying to create an array of data which will be grouped by time (field_time_value).
This is the raw result of SQL query and I operate on this data ($query):
This is the result I'd like to have (desired) - all the closed keys has an empty value:
This is what I have right now (look at the value on [15.15][data][1][data] - it's empty and according to data in $query it should be filled in, as above), all the closed keys has an empty value:
This is the code I'm using:
$days = array(
1 => t('Monday'),
2 => t('Tuesday'),
3 => t('Wednesday'),
4 => t('Thursday'),
5 => t('Friday'),
6 => t('Saturday'),
7 => t('Sunday'),
);
foreach ($query as $key => $value) {
foreach($days as $day_key => $day_name) {
if ($value->field_day_value == $day_key) {
$rows[$value->field_time_value]['data'][$day_key] = array('data' => 'Day: '.$value->field_day_value.' Hour: '.$value->field_time_value);
} else {
$rows[$value->field_time_value]['data'][$day_key] = array('data' => 'empty');
}
}
}
What am I doing wrong?
Don't bother anymore, I get the problem. There should be one more condition which will prevent from overriding data in my array:
foreach ($query as $key => $value) {
foreach($days as $day_key => $day_name) {
if ($value->field_day_value == $day_key) {
$rows[$value->field_time_value]['data'][$day_key] = array('data' => 'Day: '.$value->field_day_value.' Hour: '.$value->field_time_value);
} else {
if (!isset($rows[$value->field_time_value]['data'][$day_key])) {
$rows[$value->field_time_value]['data'][$day_key] = array('data' => 'empty');
}
}
}
}
I have the following code (I know that this code is not optimized but it's not for discussion):
function select_categories($cat_id)
{
$this->db = ORM::factory('category')
->where('parent', '=', $cat_id)
->find_all();
foreach ($this->db as $num => $category)
{
if($category->parent == 0)
{
$this->tmp[$category->parent][$category->id] = array();
}
else {
$this->tmp[$category->parent][$category->id] = array();
}
$this->select_categories($category->id);
}
return $this->tmp;
}
Function returns this array:
array(3) (
0 => array(2) (
1 => array(0)
2 => array(0)
)
2 => array(1) (
3 => array(0)
)
3 => array(2) (
4 => array(0)
5 => array(0)
)
)
But how should I change the code
else {
$this->tmp[$category->parent][$category->id] = array();
// ^^^^^^^^^^^^^^^^^^^^^^ (this bit)
}
To merge array[3] to array[2][3] for example (because array[3] is a subdirectory of array[2] and array[2] is a subdirectory of array[0][2]), so, I need to make this (when I don't know the level of subdirectories):
array (
0 => array (
1 => array
2 => array (
3 => array (
4 => array
5 => array
)
)
)
)
A long time ago I wrote some code to do this in PHP. It takes a list of entities (in your case, categories) and returns a structure where those entities are arranged in a tree. However, it uses associative arrays instead of objects; it assumes that the “parent” ID is stored in one of the associative array entries. I’m sure that you can adapt this to your needs.
function make_tree_structure ($nontree, $parent_field)
{
$parent_to_children = array();
$root_elements = array();
foreach ($nontree as $id => $elem) {
if (array_key_exists ($elem[$parent_field], $nontree))
$parent_to_children [ $elem[$parent_field] ][] = $id;
else
$root_elements[] = $id;
}
$result = array();
while (count ($root_elements)) {
$id = array_shift ($root_elements);
$result [ $id ] = make_tree_structure_recurse ($id, $parent_to_children, $nontree);
}
return $result;
}
function make_tree_structure_recurse ($id, &$parent_to_children, &$nontree)
{
$ret = $nontree [ $id ];
if (array_key_exists ($id, $parent_to_children)) {
$list_of_children = $parent_to_children [ $id ];
unset ($parent_to_children[$id]);
while (count ($list_of_children)) {
$child = array_shift ($list_of_children);
$ret['children'][$child] = make_tree_structure_recurse ($child, $parent_to_children, $nontree);
}
}
return $ret;
}
To see what this does, first try running it on a structure like this:
var $data = array (
0 => array('Name' => 'Kenny'),
1 => array('Name' => 'Lilo', 'Parent' => 0),
2 => array('Name' => 'Adrian', 'Parent' => 1)
3 => array('Name' => 'Mark', 'Parent' => 1)
);
var $tree = make_tree_structure($data, 'Parent');
If I’m not mistaken, you should get something like this out: (the “Parent” key would still be there, but I’m leaving it out for clarity)
array (
0 => array('Name' => 'Kenny', 'children' => array (
1 => array('Name' => 'Lilo', 'children' => array (
2 => array('Name' => 'Adrian')
3 => array('Name' => 'Mark')
)
)
)
Examine the code to see how it does this. Once you understand how this works, you can tweak it to work with your particular data.
Assuming you dont want any data/children tags in your array:
foreach ($this->db as $num => $category)
{
// save the data to the array
$this->tmp[$category->id] = array();
// save a reference to this item in the parent array
$this->tmp[$category->parent][$category->id] = &$this->tmp[$category->id];
$this->select_categories($category->id);
}
// the tree is at index $cat_id
return $this->tmp[$cat_id];
If you just need to retrieve the full tree out of the database, you can even simplify your query (get all records at once) and remove the recursive call in this function. You will need an extra check that will only set the $this->tmp[$catagory->id] when it does not exist and else it should merge the data with the existing data.