Jump to content

Preg_match multi line pattern?


Jantz

Recommended Posts

Hi there,

 

I was hoping someone could shed some light on how to preg_match multi line data patterns in a text file like below.

 

Data 1:

...

blah blah blah

blah

...

Data 2:

...

blah2 blah2 blah2

blah2

...

 

 

i need to return the data chunks however I cannot seem to be able to match a $start pattern to include the data chunk label (eg. Data 1: followed  by the 3 period dots on the line below).

 

Any help would be most appreciated

 

Thanks

 

 

 

 

Link to comment
Share on other sites

What pattern are you trying to use? By default the fullstop/period doesn't match a newline character. You will have to use the s modifier to force it to. Or alternatively you can use the special characters to match a certain amount of line breaks. It's not exactly clear from your question what you wish to match. It's all very well making a 'non-sense' example to ask your question, but it obfuscates the problem. Assuming you wanted to match the data between Data 1 and Data 2, then something like this should work...

 

$pattern = "#Data [0-9]+:\s{2}\K.+?(?=Data [0-9]+:|$)#si";

Link to comment
Share on other sites

Hi cags, apologies, I'm quite new to this.

 

What I am actually trying to do is return the data between found between designated start and end points in a text file. I am thinking along these lines:

 

<?php

$contents = file_get_contents('my.txt');

 

$start = 'Data 1:/n\.\.\.';

$end = '\.\.\.';

preg_match('/$start(.*)$end/s', $contents, $m);

list(,$data['data1']) = $m;

 

$start = 'Data 2:/n\.\.\.';

$end = '\.\.\.';

preg_match('/$start(.*)$end/s', $contents, $m);

list(,$data['data2']) = $m;

 

echo $data['data1'];

echo $data['data2'];

?>

 

My problem is being able to match the multi line pattern of the starting points. eg.

 

Data 1:

...

 

Hopefully I am making a little more sense now :)

 

Thanks again.

 

 

Link to comment
Share on other sites

Still not working.

 

Thanks.

 

Just for future refernce, perhaps you can give a more decriptive answer as opposed to simply responding with something like that. "Still isn't working" doesn't tell anyone anything useful. Perhaps including the latest code snippet and giving users within the thread any error / warning messages PHP is giving you. I was looking at your last snippet, and noticed you had Data 1:/n\.\.\. Is that supposed to be a newline? If so, it is wirtten as \n, and you may want to take carriage returns into account as well. Using \s is a shorthand character class that encompasses all whitespace characters (be it literal spaces, tabs, newlines, carriage returns, etc..) cags made use of this to cover all these bases.

 

Here is what I came up with (using a separate example):

 

$html = <<<EOF
Data 1:
...
blah blah blah
blah
...
Data 2:
...
blah2 blah2 blah2
blah2
...
EOF;

preg_match_all('#Data [0-9]+:\s{2}\.{3}\s+\K(?:.(?!\.{3}))+#si', $html, $matches);
echo '<pre>'.print_r($matches, true);

 

 

Whether this solution is what you are looking for or not, please be more descriptive if you want better assistance. I created a smiley for such vague occasions:  :psychic: Remember, 10/10 times, peoples' crystal balls are broken and in the shop for repairs.

Link to comment
Share on other sites

Thanks very much

 

I have a working preg_match solution for my intended (but not very well explained) purpose. You can see the final in the code below. I'm sure it looks very amateurish.. but it works for the most part thanks to your guidance.

 

Now my problem is that although my matches all work, I have a mysql insert problem. All values get inserted correctly into the database except for $data['notes'] (matched from Data 1: chunk). This seems odd. Any ideas?

 

No errors are displayed, and all other values are added to the record successfully. I can also confirm that $data['notes'] returns a result as I can echo successfully.

 

---

<?php

 

$contents = file_get_contents($my.txt);

 

preg_match('/^id: (.+)/m', $contents, $m);

list(,$data['id']) = $m;

 

preg_match('/^name: (.+)/m', $contents, $m);

list(,$data['name']) = $m;

 

preg_match('/^vendor: (.+)/m', $contents, $m);

list(,$data['vendor']) = $m;

 

preg_match('/^vendor_url: (.+)/m', $contents, $m);

list(,$data['vendorurl']) = $m;

 

preg_match("/Data 1:\s\.{3}\s(.*?)\.{3}/s", $contents, $m);

list(,$data['notes']) = $m;

 

$w1 = $data['id'];

$w2 = $data['name'];

$w3 = $data['vendor'];

$w4 = $data['vendorurl'];

$w5 = $data['notes'];

 

// Make a Connection

mysql_connect("localhost", "user", "pass") or die(mysql_error());

mysql_select_db("test") or die(mysql_error());

 

// Insert into the table

mysql_query("INSERT INTO table (id, name, vendor, vendorurl, notes) VALUES ('$w1','$w2','$w3','$w4','$w5')") or die(mysql_error());

 

?>

 

 

FYI - my text file that grab the data from

 

---my.text---

 

id: 1263294294

name: abc

vendor: def

vendor_url: www.abc.com

Data 1:

...

blah blah

blah

...

Data 2:

...

blah2 blah2

blah2

...

 

---my.text---

 

 

Thanks again. Hope no crystal balls this time. I'm trying...

 

Link to comment
Share on other sites

Ok, I have this solved.

 

With the help of you guys the final preg_match was :

preg_match("/Data 1:\s\.{3}\s(.*?)\.{3}/s", $contents, $m);
list(,$data['notes']) = $m;   

 

The reason why I was not able to insert into a mysql table is....

 

The $data['notes'] variable was only returning a value using get_file_contents('test.txt'); using a unix created source file with included carriage returns. This file was my test file for creating the script.

 

My real world source txt files were generated on a Windows PC. Because of this I had to fix by doing the following:

$contents = file_get_contents('my.txt');
$contents= str_replace("\r\n", "\n", $contents);

 

This fixed the variable and allowed $data['notes'] to return a result and subsequently successfully be inserted into the database.

 

All in all.... preg_match solved.... mysql INSERT solved.

 

Many thanks to all.

 

Link to comment
Share on other sites

This thread is more than a year old. Please don't revive it unless you have something important to add.

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...

Important Information

We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.