PHP Array to CSV
Instead of writing out values consider using fputcsv()
.
This may solve your problem immediately.
Note from comment: I should mention that this will be making a file on your server, so you'll need to read that file's contents before outputting it, also if you don't want to save a copy then you'll need to ùnlink`the file when you are done
Write array to CSV file using PHP
Use array_merge
, also I don't think you need []
while assigning to inputArr
:
$inputArr = array_merge(array($names, $gender, $age, $state), $remarks);
$fp = fopen($_SERVER["DOCUMENT_ROOT"]."/student.csv", "a+");
fputcsv($fp, $inputArr);
fclose($fp);
Array to csv download in PHP
You have to add a newline
echo $line . "\n";
Even better
echo $line . PHP_EOL; //constant for correct line-ending depending on OS.
How to convert Array to Array list for CSV export using FputCSV?
Just cast the objects to arrays with (array)
:
$file = fopen($CsvFile, 'w');
fputcsv($file, get_object_vars(reset($data)));
foreach ($data as $row) {
fputcsv($file, (array)$row);
}
fclose($file);
If the object properties and $HeaderFields
are not the same then use $HeaderFields
instead.
How to write a multidimensional array to a csv file. PHP
As you figured, fputcsv()
takes a unidimensional array as input, and saves each element in one row.
To save each array in an array, loop through the parent array and save each subarray as you would normally with fputcsv()
:
<?php
$data[] = ["JANE WILLIAMS", "6/8/1998", "55846874E", "4321"];
$data[] = ["SARAH JONES", "15/01/1982", "56897547Q", "1234"];
$data[] = ["JAMES BRENNAN", "09/05/1978", "25689514W", "8575"];
$outFile = fopen("data.csv", "w") or die("Unable to open file!");
foreach ($data as $row) {
fputcsv($outFile, $row);
}
fclose($outFile);
Write a CSV file from a PHP Array
For writing a PHP array to a CSV file you should use the built in PHP function fputcsv
:
<?php
$list = array (
array('header 1', 'header 2', 'header 3', 'header 4'),
array('5656', '454545', '5455', '5454'),
array('541212', '454545', '5455', '5454'),
array('541212', '454545', '5455', '5454'),
);
$fp = fopen('file.csv', 'wb');
foreach ($list as $fields) {
fputcsv($fp, $fields);
}
fclose($fp);
Edit:
More specific example based on your data input:
<?php
// I had to recreate your data, this is just an example
$array_of_objects = array();
for( $i = 0; $i < 5; $i++ )
{
$obj = new \stdClass();
$obj->username = "Rein";
$obj->answer = "Correct";
$obj->awesomeness = 1000;
$array_of_objects[] = $obj;
}
// Open a file to write to
$fp = fopen('file.csv', 'wb');
$i = 0;
// Loop the array of objects
foreach( $array_of_objects as $obj )
{
// Transform the current object to an array
$fields = array();
foreach ($obj as $k => $v)
{
$fields[ $k ] = $v;
}
if( $i === 0 )
{
fputcsv($fp, array_keys($fields) ); // First write the headers
}
fputcsv($fp, $fields); // Then write the fields
$i++;
}
fclose($fp);
Edit 2:
Based on new information (you have a JSON string to start with), I'm added this example as a better way to write the data to a CSV file:
<?php
$data = json_decode($_POST['data'], TRUE);
$records = $data['records'];
$fp = fopen('records.csv', 'wb');
$i = 0;
foreach ($records as $record) {
if($i === 0) {
fputcsv($fp, array_keys($record));
}
fputcsv($fp, array_values($record));
$i++;
}
fclose($fp);
PHP - Array to CSV by Column
I had to write my own function. Thought maybe it might help someone else!
/*
* The array is associative, where the keys are headers
* and the values are the items in that column.
*
* Because the array is by column, this function is probably costly.
* Consider a different layout for your array and use a better function.
*
* @param $array array The array to convert to csv.
* @param $file string of the path to write the file.
* @param $delimeter string a character to act as glue.
* @param $enclosure string a character to wrap around text that contains the delimeter
* @param $escape string a character to escape the enclosure character.
* @return mixed int|boolean result of file_put_contents.
*/
function array_to_csv($array, $file, $delimeter = ',', $enclosure = '"', $escape = '\\'){
$max_rows = get_max_array_values($array);
$row_array = array();
$content = '';
foreach ($array as $header => $values) {
$row_array[0][] = $header;
$count = count($values);
for ($c = 1; $c <= $count; $c++){
$value = $values[$c - 1];
$value = preg_replace('#"#', $escape.'"', $value);
$put_value = (preg_match("#$delimeter#", $value)) ? $enclosure.$value.$enclosure : $value;
$row_array[$c][] = $put_value;
}
// catch extra rows that need to be blank
for (; $c <= $max_rows; $c++) {
$row_array[$c][] = '';
}
}
foreach ($row_array as $cur_row) {
$content .= implode($delimeter,$cur_row)."\n";
}
return file_put_contents($file, $content);
}
And this:
/*
* Get maximum number of values in the entire array.
*/
function get_max_array_values($array){
$max_rows = 0;
foreach ($array as $cur_array) {
$cur_count = count($cur_array);
$max_rows = ($max_rows < $cur_count) ? $cur_count : $max_rows;
}
return $max_rows;
}
New Way (using a class)
I wrote a class for this a while later, which I'll provide for anyone looking for one now:
class CSVService {
protected $csvSyntax;
public function __construct()
{
return $this;
}
public function renderCSV($contents, $filename = 'data.csv')
{
header('Content-type: text/csv');
header('Content-Disposition: attachment; filename="' . $filename . '"');
echo $contents;
}
public function CSVtoArray($filename = '', $delimiter = ',') {
if (!file_exists($filename) || !is_readable($filename)) {
return false;
}
$headers = null;
$data = array();
if (($handle = fopen($filename, 'r')) !== false) {
while (($row = fgetcsv($handle, 0, $delimiter, '"')) !== false) {
if (!$headers) {
$headers = $row;
array_walk($headers, 'trim');
$headers = array_unique($headers);
} else {
for ($i = 0, $j = count($headers); $i < $j; ++$i) {
$row[$i] = trim($row[$i]);
if (empty($row[$i]) && !isset($data[trim($headers[$i])])) {
$data[trim($headers[$i])] = array();
} else if (empty($row[$i])) {
continue;
} else {
$data[trim($headers[$i])][] = stripcslashes($row[$i]);
}
}
}
}
fclose($handle);
}
return $data;
}
protected function getMaxArrayValues($array)
{
return array_reduce($array, function($carry, $item){
return ($carry > $c = count($item)) ? $carry : $c;
}, 0);
}
private function getCSVHeaders($array)
{
return array_reduce(
array_keys($array),
function($carry, $item) {
return $carry . $this->prepareCSVValue($item) . $this->csvSyntax->delimiter;
}, '') . "\n";
}
private function prepareCSVValue($value, $delimiter = ',', $enclosure = '"', $escape = '\\')
{
$valueEscaped = preg_replace('#"#', $escape . '"', $value);
return (preg_match("#$delimiter#", $valueEscaped)) ?
$enclosure . $valueEscaped . $enclosure : $valueEscaped;
}
private function setUpCSVSyntax($delimiter, $enclosure, $escape)
{
$this->csvSyntax = (object) [
'delimiter' => $delimiter,
'enclosure' => $enclosure,
'escape' => $escape,
];
}
private function getCSVRows($array)
{
$n = $this->getMaxArrayValues($array);
$even = array_values(
array_map(function($columnArray) use ($n) {
for ($i = count($columnArray); $i <= $n; $i++) {
$columnArray[] = '';
}
return $columnArray;
}, $array)
);
$rowString = '';
for ($row = 0; $row < $n; $row++) {
for ($col = 0; $col < count($even); $col++) {
$value = $even[$col][$row];
$rowString .=
$this->prepareCSVValue($value) .
$this->csvSyntax->delimiter;
}
$rowString .= "\n";
}
return $rowString;
}
public function arrayToCSV($array, $delimiter = ',', $enclosure = '"', $escape = '\\', $headers = true) {
$this->setUpCSVSyntax($delimiter, $enclosure, $escape);
$headersString = ($headers) ? $this->getCSVHeaders($array) : '';
$rowsString = $this->getCSVRows($array);
return $headersString . $rowsString;
}
}
How to create an array from a CSV file using PHP and the fgetcsv function
Like you said in your title, fgetcsv is the way to go. It's pretty darn easy to use.
$file = fopen('myCSVFile.csv', 'r');
while (($line = fgetcsv($file)) !== FALSE) {
//$line is an array of the csv elements
print_r($line);
}
fclose($file);
You'll want to put more error checking in there in case fopen()
fails, but this works to read a CSV file line by line and parse the line into an array.
Related Topics
Laravel 5.5 Ajax Call 419 (Unknown Status)
How to Do This in Laravel, Subquery Where In
Sorting a PHP Array of Arrays by Custom Order
How Does True/False Work in PHP
Laravel: Error [Pdoexception]: Could Not Find Driver in Postgresql
Insert Blobs in MySQL Databases With PHP
Global or Singleton For Database Connection
How to Get the Base Url With PHP
Submitting a Multidimensional Array Via Post With PHP
PHP: Custom Error Handler - Handling Parse & Fatal Errors
How to Resolve Ambiguous Column Names When Retrieving Results
Laravel 5 Pdoexception Could Not Find Driver
Correctly Determine If Date String Is a Valid Date in That Format