-2

Our Story: (short version below if you're eager to troubleshoot)

This question is asked after extensively searching for a way to get a multidimensional array (with named keys) back into it's CSV file. You might say: "But this is covered on multiple pages on SO, search better!" but we did, and the results we found we have tried to bend to our will, but failed.

The reason for this in the first place was to remove columns from the CSV that were interfering with the rest of our Query's and Code.

So now we're back to ask on SO:

We've read the CSV into a multidimensional Array, using the headers' 1st line as key names.

We then used unset($array[$i]['insert_date']); to remove the columns from the array

We also str_replace'd those columns names from our $header variable.

So we're extensively reading out csv's, putting them in awesome Arrays that have a numerical first index, and second dimension keys named after the first line of our CSV file.

We also have the original Header from CSV file stored in a variable handsomely called $header with a string like: '"brand";"category";"category_path"

So.. $header is a string, $array is our multidimensional array.

All we want to do, and we're stuck editing loop after loop, is to create a brand new File, that has our $header as the first line, and our $array's values as strings..

file to write to: $putfile = fopen("feeds/broken/lu-zz.csv", "rw");

we're using: fputcsv($file, $array,';','"'); to write

and preferably: \n line endings

In short:

from this:

array (size=3886)
  0 => 
    array (size=19)
      'brand' => string 'Tommy Hilfiger' (length=14)
      'category' => string '' (length=0)
      'category_path' => string 'Heren|Jeans|Blue jeans' (length=22)

  1 => 
    array (size=19)
      'brand' => string 'Marc Aurel' (length=10)
      'category' => string '' (length=0)
      'category_path' => string 'Dames|Jurken|Zomerjurken' (length=24)

  2 => 
    array (size=19)
      'brand' => string 'Rinascimento' (length=12)
      'category' => string '' (length=0)
      'category_path' => string 'Dames|Jurken|Print jurken' (length=25)

To This

"brand";"category";"category_path"
"Tommy Hilfiger";"";"Heren|Jeans|Blue jeans"  (/n)
"Marc Aurel";"";"Dames|Jurken|Zomerjurken"  (/n)
"Rinascimento";"";"Dames|Jurken|Print jurken"  (/n)

Last piece of code we tried:

{ 
    foreach($subarray as $value){
        for ($i=0, $m=count($value); $i<$m; $i++){ 
          //$test = implode('";"',$subarray) ; 
          //$tmp = array();
          $result = call_user_func_array('array_merge', $subarray);
          //$tmp[]= array_merge($subsub[$i]);
          var_dump($result);
          fputcsv($putfile, $subarray,';','"'); 

        }

    } 
}  fclose($putfile);

This just returns the same value over and over again into an array:

foreach ($array as $subarray) { 
    foreach($subarray as $value){
        for ($i=0, $m=count($value); $i<$m; $i++){ 
          //$test = implode('";"',$subarray) ; 
          //$tmp = array();

          print_r($subarray);
          fputcsv($putfile, $subarray,';','"'); 

        }

    } 
}  fclose($putfile);

Solution in our case: Thanks to "Don't Panic" & "CBroe".

$putfile = fopen("feeds/stukkefeeds/lu-zz.csv", "wb");
$header = str_replace('"','',$header1);
$titel = explode(';',$header);
var_dump($titel);
// then write in your data
    fputcsv($putfile, $titel,';','"');
foreach ($array as $line) {
    fputcsv($putfile, $line,';','"'); 
}
RkdL
  • 112
  • 11
  • Try searching SO for `convert json to csv` - results will be more to your liking – dbmitch Aug 10 '16 at 22:43
  • You've shown what you're starting with, and what you're trying to get to, which is good, but I think it would be helpful for you to include a code block that shows the code you are currently using, without any story around it, and a short explanation of what that's doing that _isn't_ what you want. – Don't Panic Aug 10 '16 at 22:50
  • how will those results help me, and what results do i need to look for to apply to php, and how does JSON work as im not asking for a JSON solution. It's a problem we haven't found on SO, We're dealing with it for 2 nights now, and the solutions we do find can't be bent to what we need it to do... – RkdL Aug 10 '16 at 22:50
  • Regarding your edit, my comment is not to explain your downvote (not mine). Just trying to be helpful. – Don't Panic Aug 10 '16 at 22:51
  • Thanks for asking, i added the last foreach we've tried, but since we've tried so many it's hard to recall what all the options were. As we're looking to other solutions on similar problems, those don't have either the dimensions like we do, or the keys are numbered.. Those solutions are short however so it looks like a foreach inside a foreach might do the trick. ill edit with another close solution we thougt we had as soon as i've recalled it.. – RkdL Aug 10 '16 at 22:55

2 Answers2

2

It looks like you may be making it more complicated than it needs to be. If you have an $array that is the one you've shown that looks like:

array (size=3886)
  0 => 
    array (size=19)
      'brand' => string 'Tommy Hilfiger' (length=14)
      'category' => string '' (length=0)
      'category_path' => string 'Heren|Jeans|Blue jeans' (length=22)
...

And you have a working file handle that you've opened with

$putfile = fopen("feeds/broken/lu-zz.csv", "w");

You shouldn't need a nested loop at all. You can get the header line by using array_keys on the first item in the array (or any item, really), write it to the file with fputcsv, and then loop over the array and write each line of data, also with fputcsv.

$first_line = reset($array);                 // get the first line
fputcsv($putfile, array_keys($first_line));  // use its keys to write the headers

// then write in your data
foreach ($array as $line) {
    fputcsv($putfile, $line,';','"'); 
}
Don't Panic
  • 41,125
  • 10
  • 61
  • 80
  • Ha, thinking the same thing at the same time :) – CBroe Aug 10 '16 at 23:08
  • Hmm, I was just thinking that, too. :) – Don't Panic Aug 10 '16 at 23:09
  • it worked. i've changed fopen to end with "wb" instead of "rw" which solved the 1kb filesize. added an explode on the `header` to make it an array. and wrote the rest as you can read in solution above. Thanks to you both for helping out! ill mark Don't Panic's answer. – RkdL Aug 10 '16 at 23:43
2

Looks like you are thinking way too complicated here ...

$firstIteration = true;
foreach($yourArray as $elem) {
  if($firstIteration ) { // if this is the first array element,
                         // write out its keys to create the CSV heading line
    echo implode(';', array_keys($elem)) .'<br>';
    $firstIteration = false;
  }
  echo implode(';', $elem) .'<br>'; // output the data for each array element
}

(Notice that I used echo and implode here for demonstration purposes; the result will not have the enclosing " - switching that out for writing CSV to the file again should be no issue.)

CBroe
  • 91,630
  • 14
  • 92
  • 150
  • well, complicated thinking is a thing in my life.... That said i am so very relieved there are still men like you and Don't Panic that aren't overeager downvoters and are still around to help new coders to the scene. about the answers given: "i see what you did there while facepalming my thinking process" and i'll give it a shot. ill report back here. – RkdL Aug 10 '16 at 23:18