i have a function what separate my file's content. Example file:
001;"text1"
002;"text2"
003;"text3"
999
001;"tekst11"
Sometimes some indexes have a few values:
120;"text2"
120;"text3"
My function:
function parseCSV($file) {
$lines = file($file);
$output = array();
$i = -1;
foreach($lines as $line) {
$line = trim($line);
if($line == "999") {
$i++;
} else {
$ex = explode(";", $line, 2);
$val = str_replace("\"", "", $ex[1]);
//$dodaj = mysql_query("INSERT INTO `czynsz` (`$ex[$i]`) VALUES ('$val')");
if(isset($output[$i][$ex[0]])) {
if(is_array($output[$i][$ex[0]])) {
$output[$i][$ex[0]][] = $val;
} else {
$output[$i][$ex[0]] = array($output[$i][$ex[0]], $val);
}
} else {
$output[$i][$ex[0]] = $val;
}
$dodaj = mysql_query("INSERT INTO `czynsz` (`$ex[$i]`) VALUES ('$val')");
}
}
return $output;
}
$csvdata = parseCSV("woda.txt");
echo "<pre>\r\n";
print_r($csvdata);
echo "</pre>\r\n";
Above script makes me multi-level array tree and separate arrays from themselves by separator (999), because in my file are many arrays... When an index has many values - the script makes for him internal tree. For example:
Array
(
[0] => Array
(
[001] => 06-001-03-13
[002] => 06447
[003] => F
...
[097] =>
[120] => Array
(
[0] => text1
[1] => text2
)
)
[1] => Array
...
And there is my question:
I have a problem with save this mega array in my MySQL base. Every index in array have the same in data base. When the same index will have many values (ex. 120) it can be implode. Thank you with all my heart for any form of help... :(
Create a MySQL Table:
CREATE TABLE `czynsz` (
`id` INT NOT NULL ,
`value` VARCHAR( 255 ) NOT NULL
) ENGINE = InnoDB;
ALTER TABLE `czynsz` ADD UNIQUE `unique` ( `id` )
Then use the following php code to insert the data
ini_set('error_reporting', E_ALL); // just for debugging remove later
ini_set('display_erorrs', 1); // just for debugging remove later
function parseCSV($file) {
$lines = file($file);
$output = array();
$i = 0;
foreach($lines as $line) {
$line = trim($line);
if($line == "999") {
$i++;
continue;
}
list($id, $val) = explode(";", $line, 2);
$val = str_replace("\"", "", $val);
$result = mysql_query("
INSERT INTO `czynsz` (
id,
`value`
) VALUES (
'$id',
'$val'
) ON DUPLICATE KEY UPDATE
`value` = CONCAT(`value`, ', ', '$val')"
);
if(!$result) {
die(mysql_error());
}
if(isset($output[$i][$id])) {
if(is_array($output[$i][$id])) {
$output[$i][$id][] = $val;
} else {
$output[$i][$id] = array($output[$i][$id], $val);
}
} else {
$output[$i][$id] = $val;
}
}
return $output;
}
Use the PHP sledgehammer solution...
Assuming that you just want to store the array and don't need to query against distinct nodes, use the serialize function to turn your array into a string representation. You can easily pull the data and then use unserialize to get back the original array.
$s_arr = serialize($my_array);
$my_array = unserialize($s_arr);
If you need access to the nodes in the database, then I think that MySQL is not a good solution because of the complexity involved. If you want a key-value store, then you should look at a NoSQL solution such as Redis.
Related
I want to populate a html table from the results of a SQL query, the fields included will vary depending on choices the user makes so I want to autmatically set the headings etc based on what is in the results of the query. I found the array_to_table function on the website https://inkplant.com/code/array-to-table and it does what I want except the data is duplicated:-
Expected result
Formation Play
A SW
S DL
Actual Result
Formation 0 Play 1
A A SW SW
S S DL DL
I think it may be be to do with the type of array I'm creating but I'm unsure how to alter the code to generate my expected result. I'm not sure if I should create the array in a different way or whether (or how) I should change the function to work with the type of array I have.
#SQL for creating example table
CREATE TABLE `example` ( `id` INT NOT NULL AUTO_INCREMENT , `form` VARCHAR(10) NOT NULL , `playcall` VARCHAR(10) NOT NULL , PRIMARY KEY (`id`)) ENGINE = InnoDB;
#Sample data
INSERT INTO `example` (`id`, `form`, `playcall`) VALUES (NULL, 'A', 'SW'), (NULL, 'S', 'DL');
#mycode
$sql = "SELECT `form` as 'Formation',`playcall` as 'Playcall' FROM `example` ORDER BY `form` DESC";
$res = execute_db($sql3 $conn);
$caption = "Example table";
echo array_to_table($res,$caption);
#function
function array_to_table($data,$caption,$args=false) {
if (!is_array($args)) { $args = array(); }
foreach (array('class','column_widths','custom_headers','format_functions','nowrap_head','nowrap_body','capitalize_headers') as $key) {
if (array_key_exists($key,$args)) { $$key = $args[$key]; } else { $$key = false; }
}
if ($class) { $class = ' class="'.$class.'"'; } else { $class = ''; }
if (!is_array($column_widths)) { $column_widths = array(); }
//get rid of headers row, if it exists (headers should exist as keys)
if (array_key_exists('headers',$data)) { unset($data['headers']); }
$t="<table style='width:40%' class='w3-table w3-striped w3-bordered'>";
$t .= $caption;
$i = 0;
foreach ($data as $row) {
$i++;
//display headers
if ($i == 1) {
foreach ($row as $key => $value) {
if (array_key_exists($key,$column_widths)) { $style = ' style="width:'.$column_widths[$key].'px;"'; } else { $style = ''; }
$t .= '<col'.$style.' />';
}
$t .= '<thead><tr>';
foreach ($row as $key => $value) {
if (is_array($custom_headers) && array_key_exists($key,$custom_headers) && ($custom_headers[$key])) { $header = $custom_headers[$key]; }
elseif ($capitalize_headers) { $header = ucwords($key); }
else { $header = $key; }
if ($nowrap_head) { $nowrap = ' nowrap'; } else { $nowrap = ''; }
$t .= '<td'.$nowrap.'>'.$header.'</td>';
}
$t .= '</tr></thead>';
}
//display values
if ($i == 1) { $t .= '<tbody>'; }
$t .= '<tr>';
foreach ($row as $key => $value) {
if (is_array($format_functions) && array_key_exists($key,$format_functions) && ($format_functions[$key])) {
$function = $format_functions[$key];
if (!function_exists($function)) { custom_die('Data format function does not exist: '.htmlspecialchars($function)); }
$value = $function($value);
}
if ($nowrap_body) { $nowrap = ' nowrap'; } else { $nowrap = ''; }
$t .= '<td'.$nowrap.'>'.$value.'</td>';
}
$t .= '</tr>';
}
$t .= '</tbody>';
$t .= '</table>';
return $t;
}
EDIT: Based on the tip from https://stackoverflow.com/users/13851118/dhnwebpro I dumped the array to see what it contained:-
Array
(
[0] => Array
(
[Formation] => A
[0] => A
[Playcall] => SW
[1] => Sw
)
[1] => Array
(
[Formation] => S
[0] => S
[Playcall] => DL
[1] => DL
)
)
EDIT2: I changed the format of the query and got it working:-
$res3 = $conn->query($sql3)->fetchAll(PDO::FETCH_ASSOC);
Fetch both was indeed the default and I was able to override that with the above statement.
As #dhnwebpro said PDO was defaulting to PDO::FETCH_BOTH so I overrode it by changing the execution to:-
$res3 = $conn->query($sql3)->fetchAll(PDO::FETCH_ASSOC);
I want to extract some data and create a csv file. This is how my attributes table looks like. you can see it in the picture:
HERE
This is my code, what i tried:
$select = mysql_query("select * from attributes");
$final ="";
$i = 0;
while($row = mysql_fetch_array($select)) {
$id_produs = $row['id_produs'];
$n_attr = $row['nume_attr'];
$val = $row['val_attr'];
$final .= $id_produs . "%%" . $val . "%%";
$csv_array_attributes[$i] = $final;
$i++;
}
This is the part when i create the CSV file:
$file = fopen("attributes.csv", "w+");
foreach ($csv_array_attributes as $line) {
fputcsv($file, explode('%%', $line), "^", "`");
}
fclose($file);
AND this would be the wanted result: HERE. So, the nume_attr should be the header for every column in the csv and the val_attr should be the values for every nume_attr (see the image).
I tried many ways but I don't get this result from the image. I have to mention that my table "attributes" has more than 74000 rows.
This is the table structure:
CREATE TABLE `attributes` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`id_produs` text NOT NULL,
`nume_attr` text NOT NULL,
`val_attr` text NOT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=673912 DEFAULT CHARSET=latin1;
/*Try following code */
$select = mysql_query("select * from attributes");
$i = 0;
$csv_array_attributes[$i]=array('sku','manufacturer_article','manufacturer');
$i++;
while($row = mysql_fetch_array($select)) {
$csv_array_attributes[$i] =array('sku'=>$row['id_produs'],'manufacturer_article'=>$row['nume_attr'],'manufacturer'=>$row['val_attr']);
$i++;
}
$file = fopen("attributes.csv", "w+");
foreach ($csv_array_attributes as $line) {
fputcsv($file,$line);
}
fclose($file);
Let's assume speed isn't the issue here and neither is concurrency, i.e. you just want the result now no matter how good, bad or ugly the solution is ;-)
First query all the attribute names via SELECT DISTINCT nume_attr FROM attributes
Store those names as keys of an array with empty string values, i.e. you should have an array like
$template = array(
'Manufacturer Article' => '',
'Manufacturer' => '',
...
)
Make a variable that stores the currently processed id_produs (start with false).
Make a variable that stores the current "csv"-record ( again start with false )
Query all records ordered by id_produs and iteratore over the result.
If the current record has a different id_produs than the "currently processed" write out the current "csv"-array and start anew with the template array created in the first step and the current id_produs as ...the current id_produs. For each record write the val_attr value to the key nume_attr in the csv array.
You will have to check/write the last record after the iteration.
/* try following code,and reply if it will helpful to you or not */
$select = mysql_query("select * from attributes");
$i = 0;
$i++;
while($row = mysql_fetch_array($select)) {
$csv_array_attributes[$row['id_produs']][$row['nume_attr']] =$row['val_attr'];
$i++;
}
$arraytempheader=array();
$arraytemp=array();
$arraytempheader[0]="";
$j=1;
foreach ($csv_array_attributes as $Colname=>$alline) {
if($j!=1)
{
foreach($arraytempheader as $key=>$val)
{
if($key!=$j && $key!=0)
$arraytemp[$Colname][$key]="";
}
}
foreach ($alline as $keyline=>$valline)
{
$arraytempheader[$j]=$keyline;
$arraytemp[$Colname][$j]=$valline;
$j++;
}
}
$file = fopen("attributes.csv", "w+");
fputcsv($file,$arraytempheader);
foreach ($arraytemp as $Colname=>$alline) {
$finalArray=array();
$finalArray[]=$Colname;
$finalArray=array_merge($finalArray,$alline);
fputcsv($file,$finalArray);
}
fclose($file);
Try to fix this in other way.
Here you select the attributes and store them into array
$select = mysql_query("select * from attributes");
$rezultat=array();
while($row = mysql_fetch_array($select)) {
$id_produs = $row['id_produs'];
$n_attr = $row['nume_attr'];
$val = $row['val_attr'];
//$final .= $id_produs . "%%" . $val . "%%";
$rezultat[] = array('id'=>$id_produs,'attr'=>$val);
}
And here you write them to the file.
$file = fopen("attributes.csv", "w+");
foreach ($rezultat as $line) {
fputcsv($file, $line, "^", "`");
}
fclose($file);
I have an array which comes from a report.
This report has info similar to:
157479877294,OBSOLETE_ORDER,obelisk,19/01/2013 01:42pm
191532426695,WRONG_PERFORMANCE,g3t1,19/01/2013 01:56pm
159523681637,WRONG_PERFORMANCE,g3t1,19/01/2013 01:57pm
176481653889,WRONG_PERFORMANCE,g4t1,19/01/2013 01:57pm
167479810401,WRONG_PERFORMANCE,g4t1,19/01/2013 02:00pm
172485359309,WRONG_PERFORMANCE,g4t2,19/01/2013 02:02pm
125485358802,WRONG_PERFORMANCE,g4t2,19/01/2013 02:02pm
172485359309,DAY_LIMIT_EXCEEDED,obelisk,19/01/2013 02:03pm
125485358802,DAY_LIMIT_EXCEEDED,obelisk,19/01/2013 02:03pm
What I need to do is get the total of each type of error and the location so for the first would be error: 'OBSOLETE_ORDER' and location: 'obelisk'. I have tried to do this a number of ways but the best I can come up with is a multi dimensional array:
$error_handle = fopen("$reportUrl", "r");
while (!feof($error_handle) )
{
$line_of_text = fgetcsv($error_handle, 1024);
$errorName = $line_of_text[1];
$scannerName = $line_of_text[2];
if($errorName != "SCAN_RESULT" && $errorName != "" && $scannerName != "SCAN_LOGIN" && $scannerName != "")
{
$errorsArray["$errorName"]["$scannerName"]++;
}
}
fclose($error_handle);
print_r($errorsArray);
gives me the following:
Array ( [OBSOLETE_ORDER] => Array ( [obelisk] => 1 ) [WRONG_PERFORMANCE] => Array ( [g3t1] => 2 [g4t1] => 2 [g4t2] => 2 ) [DAY_LIMIT_EXCEEDED] => Array ( [obelisk] => 2 ) )
which is great...except how do I then take that apart to add to my sql database?! (I am interested in getting the key and total of that key under the key the array is under)
and then add it to the tables
-errors-
(index)id_errors
id_event
id_access_scanner
id_errors_type
total_errors
-errors_type-
(index)id_errors_type
name_errors_type
-access_scanner-
(index)id_access_scanner
id_portal
name_access_scanner
PLEASE HELP!
Thanks!
A multidimensional array is more than you need. The approach to take is to create your own string ($arrayKey in my example) to use as an array key that combines the scanner name and the error so that you can get a count.
//this is the array containing all the report lines, each as an array
$lines_of_text;
//this is going to be our output array
$errorScannerArray = array();
//this variable holds the array key that we're going to generate from each line
$arrayKey = null;
foreach($lines_of_text as $line_of_text)
{
//the array key is a combination of the scanner name and the error name
//the tilde is included to attempt to prevent possible (rare) collisions
$arrayKey = trim($line_of_text[1]).'~'.trim($line_of_text[2]);
//if the array key exists, increase the count by 1
//if it doesn't exist, set the count to 1
if(array_key_exists($arrayKey, $errorScannerArray))
{
$errorScannerArray[$arrayKey]++;
}
else
{
$errorScannerArray[$arrayKey] = 1;
}
}
//clean up
unset($line_of_text);
unset($arrayKey);
unset($lines_of_text);
//displaying the result
foreach($errorScannerArray as $errorScanner => $count)
{
//we can explode the string hash to get the separate error and scanner names
$names = explode('~', $errorScanner);
$errorName = $names[0];
$scannerName = $names[1];
echo 'Scanner '.$scannerName.' experienced error '.$errorName.' '.$count.' times'."\n";
}
$list = array();
foreach ($lines as $line) {
$values = explode(',' $line);
$error = $values[1];
$scanner = $values[2];
if (!isset($list[$error])) {
$list[$error] = array();
}
if (!isset($list[$error][$scanner])) {
$list[$error][$scanner] = 1;
} else {
$list[$error][$scanner]++;
}
}
To go through each result I just did the following:
foreach ($errorsArray as $errorName=>$info)
{
foreach ($info as $scannerName=>$total)
{
print "$errorName -> $scannerName = $total </br>";
}
}
and now will just connect it to the sql
With your edited question, this much simpler loop will work for you, you just need to then insert the data into your database inside the loop, instead of echoing it out:
$errorsArray = Array (
[OBSOLETE_ORDER] => Array (
[obelisk] => 1
)
[WRONG_PERFORMANCE] => Array (
[g3t1] => 2
[g4t1] => 2
[g4t2] => 2
)
[DAY_LIMIT_EXCEEDED] => Array (
[obelisk] => 2
)
)
foreach($errorsArray as $row => $errors) {
foreach($errors as $error => $count) {
echo $row; // 'OBSOLETE_ORDER'
echo $error; // 'obelisk'
echo $count; // 1
// insert into database here
}
}
OLD ANSWER
You just need a new array to hold the information you need, ideally a count.
Im assuming that the correct data format is:
$report = [
['157479877294','OBSOLETE_ORDER','obelisk','19/01/2013 01:42pm'],
['191532426695','WRONG_PERFORMANCE','g3t1','19/01/2013 01:56pm'],
['159523681637','WRONG_PERFORMANCE','g3t1','19/01/2013 01:57pm'],
['176481653889','WRONG_PERFORMANCE','g4t1','19/01/2013 01:57pm'],
.....
];
foreach($report as $array) {
$errorName = $array[1];
$scannerName = $array[2];
if(exists($errorsArray[$errorName][$scannerName])) {
$errorsArray[$errorName][$scannerName] = $errorsArray[$errorName][$scannerName] + 1;
}
else {
$errorsArray[$errorName][$scannerName] = 1;
}
}
I have following records in text file, need to extract that record form text file and treat them as seperate array variables
r1=(1,2,3)|r2=(4,5,6)|r3=(1,2,3,4,5,7)|rn=(9,6,7,8) seperated by pipe(|)
I need to represent that as array use seperately like below
$r1= Array
(
[0] => 1
[1] => 2
[2] => 3
)
$r2=Array
(
[0] => 4
[1] => 5
[2] => 6
)
I have no idea how to do it, is it possible in php?
Just a plain regular expression to break up the string, followed by an explode on each group:
if (preg_match_all('#(\w+)=\(([\d,]*)\)#', $s, $matches)) {
foreach ($matches[2] as $i => $groups) {
$group_name = $matches[1][$i];
$$group_name = array_map('intval', explode(',', $groups));
}
}
print_r($r1);
print_r($r3);
print_r($rn);
You can use Eval
//Assuming you can pull the content from text file using fread
$temp = "r1=(1,2,3)|r2=(4,5,6)";
$temp=str_replace("=","=array",$temp);
$split=explode("|",$temp);
echo "<pre>";
foreach($split as $k=>$v){
$v="$".$v.";";
//Evaluate a string as PHP code .i.e You will get r1,r2 as a variable now which is array
eval($v);
}
print_r($r1);
print_r($r2);
$data = "r1=(1,2,3)|r2=(4,5,6)|r3=(1,2,3,4,5,7)|rn=(9,6,7,8)";
$arr = explode("|", $data);
$finArray = array();
foreach($arr as $key=>$value)
{
$single = explode('(', $value);
$finArray[] = explode(',', str_replace(')', '', $single[1]));
}
print_r($finArray);
can be done as:
$string="r1=(1,2,3)|r2=(4,5,6)|r3=(1,2,3,4,5,7)|rn=(9,6,7,8)";
$string=str_repla("r1=","",$string);
$yourArray=explode('|', $string);
This code will help you:--
<?php
$file = "/tmp/file1.txt"; // this is your file path
$f = fopen($file, "r");
while ( $line = fgets($f, 1000) ) {
print $line;
$a=explode('|',$line);
print_r($a); // I have explode based on | for you...
foreach($a as $key=>$value)
{
print_r($value);
}
fclose($file);
}
?>
""or""
$a="r1=(1,2,3)|r2=(4,5,6)|r3=(1,2,3,4,5,7)|rn=(9,6,7,8)";
$a=explode('|',$a);
print_r($a);
<?php
$file = "file.txt";
$f = fopen($file, "r");
while ( $line = fgets($f, 1000) ) {
$str = $line;
}
$str1 = explode("|",$str);
foreach($str1 as $temp) {
$str2 = explode("=",$temp);
$data[$str2[0]] = explode(",",trim($str2[1],"()"));
}
echo '<pre>';
print_r($data);
echo '</pre>';
?>
This will do your job.
I have the following code:
$rt1 = array
(
'some_value1' => 'xyz1',
'some_value2' => 'xyz2',
'value_1#30'=>array('0'=>1),
'value_2#30'=>array('0'=>2),
'value_3#30'=>array('0'=>3),
'value_1#31'=>array('0'=>4),
'value_2#31'=>array('0'=>5),
'value_3#31'=>array('0'=>6),
'some_value3' => 'xyz3',
'some_value4' => 'xyz4',
);
$array_30 = array
(
'0'=>1,
1=>'2',
2=>'3'
);
$array_31 = array
(
'0'=>4,
'1'=>'5',
'2'=>'6'
);
I need to make it an array and insert the array_30 and array_31 into a DB.
foreach($rt1 as $value){
$rt2[] = $value['0'];
}
The question was updated, so here is an updated answer. Quick check, you should really try and update this to whatever more generic purpose you have, but as a proof of concept, a runnable example:
<?php
$rt1 = array
(
'some_value1' => 'xyz1',
'some_value2' => 'xyz2',
'value_1#30'=>array('0'=>1),
'value_2#30'=>array('0'=>2),
'value_3#30'=>array('0'=>3),
'value_1#31'=>array('0'=>4),
'value_2#31'=>array('0'=>5),
'value_3#31'=>array('0'=>6),
'some_value3' => 'xyz3',
'some_value4' => 'xyz4',
);
$finalArrays = array();
foreach($rt1 as $key=>$value){
if(is_array($value)){
$array_name = "array_".substr($key,-2);
${$array_name}[] = $value['0'];
}
}
var_dump($array_30);
var_dump($array_31);
?>
will output the two arrays with the numbers 1,2,3 and 4,5,6 respectivily
i assume you want to join the values of each of the second-level arrays, in which case:
$result = array();
foreach ($rt1 as $arr) {
foreach ($arr as $item) {
$result[] = $item;
}
}
Inspired by Nanne (which reminded me of dynamically naming variables), this solution will work with every identifier after the \#, regardless of its length:
foreach ( $rt1 as $key => $value )
{
if ( false == strpos($key, '#') ) // skip keys without #
{
continue;
}
// the part after the # is our identity
list(,$identity) = explode('#', $key);
${'array_'.$identity}[] = $rt1[$key]['0'];
}
Presuming that this is your actual code, probably you will need to copy the array somewhere using foreach and afterwards create the new array as you wish:
foreach($arr as $key => $value) {
$arr[$key] = 1;
}