简体   繁体   中英

Unexpected Behavior when Parsing Text File

I am learning PHP, & right now I'm stuck. I am reading a .txt file in the script. The file contents are like this:

joe:secret
root:admin

I can read the file easily using the file() function, which returns an array. I store the data in aa variable as:

$data = file('location/file.txt');

Next I use foreach loop, and then I explode each line, and store its contents in a variable again. Then I put checks on the variable, but this is where I get behavior which I don't understand.

foreach ($data as $d) {
  $row = explode(":", $d);

  if ($row[0] == "joe" && $row[1] == "secret") {
    echo "match found ";
  }
}

The above code does give expected output. Why is that? If I do this,

echo $row[0]; echo $row[1];

then I do receive correct output. So I don't get why my check fails?

This one was tricky; I don't blame you for not catching this :)

So first, let's investigate with the php -a interactive shell:

php > $data = file('test.txt');
php > var_dump($data);
array(3) {
  [0]=>
  string(11) "joe:secret
"
  [1]=>
  string(11) "root:admin
"
  [2]=>
  string(1) "
"
}

See how the closing quote is on a separate line? That's because the \\n 's at the end of each line are kept inside each array element in $data . So $row[1] doesn't equal "secret" ; it equals "secret\\n" . To fix this, all we need is rtrim() :

foreach ($data as $line) {
  $line = rtrim($line);
  $row = explode(":", $line);

  if ($row[0] == "joe" && $row[1] == "secret") {
    echo "Match found for joe!";
  }
}

Now, it works as expected:

php > $data = file('test.txt');
php > foreach ($data as $line) {
php {   $line = rtrim($line);
php {   $row = explode(":", $line);
php {
php {   if ($row[0] == "joe" && $row[1] == "secret") {
php {     echo "Match found for joe!";
php {   }
php { }
Match found for joe!
php >

Edit: We could also use file_get_contents() instead of file() , so we just get the file contents as a string, and convert it into an array ourselves:

$data = file_get_contents('test.txt');
foreach (explode("\n", $data) as $line) {
  $row = explode(":", $line);

  if ($row[0] == "joe" && $row[1] == "secret") {
    echo "Match found for joe!";
  }
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM