Searching a CSV with PHP Given a string, I've done the below to search a CSV for a keyword and display the row if it's found

&lt;?php 
$ch = fopen("test.csv", "r");
$header_row = fgetcsv($ch);

/* This will loop through all the rows until it reaches the end */
while(($row = fgetcsv($ch)) !== FALSE) {
    $cols = array($row[0], $row[1], $row[2], $row[3]);
    if (in_array("text", $cols)) {
        echo '&lt;div&gt;'.$row[0].' | '.$row[1].' | '.$row[2].' | '.$row[3].' &lt;/div&gt;';
    }
?&gt;


I'm worried it's not best optimised for my needs, especially as the search is not regex'd and its assuming a X number of columns
Useless transformation

Since fgetcsv() returns an indexed array, the statement  

$cols = array($row[0], $row[1], $row[2], $row[3]);  

is totally useless: it results in $cols which is exactly the same as $row.

Using any number of columns

BTW, the above already answers part of your concern, regarding:


  its assuming a X number of columns


Directly working with $rows you keep all original columns.

The last part is that this statement:

echo '&lt;div&gt;'.$row[0].' | '.$row[1].' | '.$row[2].' | '.$row[3].' &lt;/div&gt;';

can be replaced by:

echo '&lt;div&gt;' . implode(' | ', $row) . ' &lt;/div&gt;';

Then, again, you'll get the exact content, whatever is the number of columns.

So your whole code can be reduced like this:

$ch = fopen("test.csv", "r");
$header_row = fgetcsv($ch);

/* This will loop through all the rows until it reaches the end */
while($row = fgetcsv($ch)) {
    if (in_array("text", $row)) {
        echo '&lt;div&gt;' . implode(' | ', $row) . ' &lt;/div&gt;';
    }
}


NOTE: if (in_array("text", $cols)) is enough and you don't need to look for FALSE, since fgetcsv() doesn't return falsy value other than FALSE itself.

Any not empty content is obviously not FALSE, and an empty line returns [0 =&gt; null], as stated by the manual:


  A blank line in a CSV file will be returned as an array comprising a single null field, and will not be treated as an error.


Using regexes

There is no need to use regexes: you're looking for a unique precise value, so in your case it'll be overkill!

It might not be the same if, for example, you wanted to find "text" even if it's only part of one (or more) column content.

Then you should do something like this:

if (preg_match('/text/', implode('', $row)))

Here we had to turn $row content into a string before applying the pattern.
But this can be improved in the context of your snippet: do implode() only once, so it will be alredy done for the echo, while the additional | doesn't matter for the preg_match.

This way, it'll result in:

while($row = fgetcsv($ch)) {
    if (preg_match('/text/', $row = implode(' | ', $row))) {
        echo '&lt;div&gt;' . $row . ' &lt;/div&gt;';
    }
}