Forum Moderators: coopster

Message Too Old, No Replies

preg replace 2 variables error

         

jman11

4:27 am on Nov 12, 2009 (gmt 0)

10+ Year Member



im getting an error code around the bolded area below, its when i use 2 variables, like if i just use $1, it will work, but if i use $new2[$1], then it comes up with this error:

Parse error: syntax error, unexpected '$', expecting T_STRING or T_VARIABLE or T_NUM_STRING


$lol = preg_match_all("/\\\cf([1-9]+)/is",$contents,$new2);

$root = array("/color([1-9]+)/is" => "<span style=\"color: rbg([b]$new2[$1][/b]);\">");

$keys = array_keys($root); // Array keys
$vals = array_values($root); // Array values
$contents = preg_replace($keys,$vals,$contents);

TheMadScientist

4:43 am on Nov 12, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member Top Contributors Of The Month



$1 is not a valid variable...
Variables cannot start with a number.
(Must start with an _ or letter: PHP Variable Basics [php.net])

Did you mean array piece 1?
$new2[1]

jman11

4:52 am on Nov 12, 2009 (gmt 0)

10+ Year Member



no... ok in regex the parenthesis () represent the variable $1, and if you do it again, its $2. like this:
(.*?) will make it be able to call $1, and it means anything there can be called.

anyways, that doesnt cause the problem because i can call $1 without $new2 just fine. any other suggestions?

TheMadScientist

6:38 am on Nov 12, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member Top Contributors Of The Month



I understand how regular expressions and their back-references (not 'variables') work. I also understand how variables within quotes work, so are you sure $1 is not the problem, since the line precedes the regex and PHP, by default, attempts to expand variables within " ", but within ' ' variables are not expanded? (This means PHP attempts to expand $new2[$1], even if $1 is ignored when alone, because it's not a valid PHP variable.)

This will not error:
$root = array("/color([1-9]+)/is" => '<span style="color: rbg('.$new2['$1'].');">');

Neither will this:
$root = array("/color([1-9]+)/is" => "<span style=\"color: rbg(".$new2["\\1"].");\">");

Or this:
$root = array("/color([1-9]+)/is" => "<span style=\"color: rbg(".$new2['\\1'].");\">");

But I'm still not sure if it's correct for what you're looking for, because your match is stored as $new2[MATCHnumber] not $new2[10122], so IMO defining your color match of 1 or more numbers as a reference to $new2[NUM] will probably not return you the correct result even if you get the regex back-reference to work, because the chances are you do not have more than a few array pieces for $new2[]...

$lol = preg_match_all("/\\\cf([1-9]+)/is",$contents,$new2);

$root = array("/color([1-9]+)/is" => "<span style=\"color: rbg($new2[$1]);\">");

$keys = array_keys($root); // Array keys
$keys = 'color10122';

$vals = array_values($root); // Array values
$vals = '<span style="color: rbg($new2[$1]);">';

$contents = preg_replace($keys,$vals,$contents);
$contents = preg_replace("/color([1-9]+)/is","<span style="color: rbg($new2[10122]);">",$contents);

I could be misunderstanding, but I think your logic is off a bit...

Anyway, sorry if I sound blunt... IMO $1 is the issue causing the error because $new2[] is within "" in an array where it is expanded as a PHP variable, rather than the regex where $1 would be treated as a back-reference... My guess is the reason it works without the $new2[] is because PHP tries to expand $new2[ARRAYpiece] within the "", which means it 'sees' $1 which is not a proper array piece, but ignores $1 with "" since it is not a valid variable.

I apologize for rambling and being 'non-specific' in places... The short version is $1 and the expansion of variables within "" is the issue.

EDITED: Clarification.

TheMadScientist

7:49 am on Nov 12, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member Top Contributors Of The Month



This would be a better way to type what I was thinking above...

$root = array("/color([1-9]+)/is" => "<span style=\"color: rbg($new2[$1]);\">");

$keys = array_keys($root); // Array keys
$keys = '/color([1-9]+)/is';

$vals = array_values($root); // Array values
$vals = '<span style="color: rbg($new2[$1]);">';

$contents = 'color10122';
$contents = preg_replace($keys,$vals,$contents);

Translates to:
$contents = preg_replace("/color([1-9]+)/is","<span style="color: rbg($new2[10122]);">",$contents);

jman11

5:37 pm on Nov 12, 2009 (gmt 0)

10+ Year Member



Ok yeh, inside the $root array though, think of it like bb code replacement, theres a lot of replacements to happen. So i have an array ($lol) which has the rbg code for the specified color, so im trying to replace the 'color{num}' with span. the {num} following 'color' will be a number, and i want to take that number, and find it in the array of rbg colors, then replace it back within <span>. its hard to explain. i got it semi working with the:

$root = array("/color([1-9]+)/is" => '<span style="color: rbg('.$new2['$1'].');">'); 

but like your saying, now the $1 really isnt working at all. any other work arounds that will fit what im doing more easily?

TheMadScientist

1:59 am on Nov 13, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member Top Contributors Of The Month



What's the difference between $contents in the two of these?

$lol = preg_match_all("/\\\cf([1-9]+)/is",$contents,$new2);
$contents = preg_replace($keys,$vals,$contents);

Could you post a snipit of each string you are searching, because I really don't understand how you are making a single match in the first part of the code, then needing to match it in the second, rather than just matching it once in the second, so there must be something I'm missing...

The two matches above both look like they work on the same string but that doesn't make sense to me with what you are asking, so I think it would help if you posted a snipit of what the first match is looking for (storing) and the value it needs to replace to in the second.

The way it looks is you could just do it all in one:
$root = array("/color([1-9]+)/is" => '<span style="color: rbg(\\1);">');

But the way you wrote it makes it sound like you are trying to relate two different values EG in array 1: blue=000099; Then when you get 'blue' in the second you want to replace it with 000099?

I really need to see what you are working with to give you very solid advice...

jman11

2:05 am on Nov 13, 2009 (gmt 0)

10+ Year Member




$contents = "some string";

$lol = preg_match_all("/color([1-9]+)/is",$contents,$new2); // This is to find the code after color, then i will put the code behind \doodle below and replace it with span color and echo it in $new2, with the [$1] behind it because its an array

$root = array("/doodle([1-9]+)/is" => '<span style="color: rbg('.$new2.'[$1]);">');

$keys = array_keys($root); // Array keys
$vals = array_values($root); // Array values
$contents = preg_replace($keys,$vals,$contents);
echo $contents;

i want to get a value from one section, and then take that value, and then replace another section, with that number basiclly if that makes sense.

TheMadScientist

3:07 am on Nov 13, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member Top Contributors Of The Month



i want to get a value from one section, and then take that value, and then replace another section, with that number basiclly if that makes sense.

What are you basing the 'later' replacement on to not replace the current value with the current value? You only have one value per array piece in $new2. You are currently trying to match the value found in the preg_replace to the value of $new2[] array piece, but there's only one value stored in each and if there's a match, then the value of $new2[] is exactly the same as the value you are replacing with $new2[]...

I don't get what you are trying to do, because even if the preceding word (doodle) is different the fact is you only have one value stored in $new2[] and even if it was in the key also so you could access the color code it still must match the color matched in the preg_replace, so it seems unnecessary to have $new2[].

I really don't understand what you're trying to do, except store a value in an array, then replace the same value with the value stored later, which does not change anything, except the code surrounding the value, which makes storing the value and trying to access it pointless, since you can just back-reference the same value and not worry about storing it.

jman11

4:13 am on Nov 13, 2009 (gmt 0)

10+ Year Member



i dont only have 1 value stored in new2, there are several, its getting rbg colors for the span, they are stored at the top of the document, as like color1, then the dag will be color1, for example, i want the take the "1" from color 1, match it with the first finding of \color

TheMadScientist

4:26 am on Nov 13, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member Top Contributors Of The Month



Could you post a snipit of each string you are searching?

K, well this is probably something I could write fairly quickly, but I really can't answer any better unless you show me exactly what you are working with rather than trying to explain it... Maybe someone else can, but for me it's way easier to write code when I can see a sample of what's involved rather than trying to guess at what it is.

If you want me to try and help you out some more, will you please post the code you just now said is at the top of the page (where you get the new color values), exactly the way it is (just a piece of it will be fine if it's long) and a sample of the string you are trying to replace the color(s) in?

Here's a thread with some short code examples in it, so you know what I mean. You can copy and paste, then run any of the examples in there to see how they work.

[webmasterworld.com...]

jman11

4:44 am on Nov 13, 2009 (gmt 0)

10+ Year Member



what im trying to do is translate rtf into html, because im trying to make a CMS just for learning experience ( i dont actually have a website to try and get traffic off of ). it takes rtf code, with file_get_contents of uploaded file. if you want some format information google "rich text format version 1.5 specification". anyways heres the code.


$contents = file_get_contents($_FILES["file"]["tmp_name"]);

$lol = preg_match_all("/\\\cf([1-9]+)/is",$contents,$new2);
$root = array("/\\\\red([0-9]+)\\\\green([0-9]+)\\\\blue([0-9]+)/is" => "<span style=\"color: rbg($1,$2,$3)\">","/\\\cf([1-9]+)/is" => '<span style="color: rbg($1);">');

$keys = array_keys($root); // Array keys
$vals = array_values($root); // Array values
$contents = preg_replace($keys,$vals,$contents); // Replacement ( parsing )
echo $contents;

the format for the rbg at the top is:
\red255\green0\blue0

TheMadScientist

5:12 am on Nov 13, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member Top Contributors Of The Month



I'm guessing you're working with something like the following and this is where I would start...
(I'd get it working then shorten and revise for efficiency.)


$colorString='{\colortbl;\red0\green0\blue0;\red0\green0\blue255;\red0\green255\blue255;
\red0\green255\blue0;\red255\green0\blue255;\red255\green0\blue0;\red255\green255\blue0;
\red255\green255\blue255;\red0\green0\blue128;\red0\green128\blue128;\red0\green128\blue0;
\red128\green0\blue128;\red128\green0\blue0;\red128\green128\blue0;\red128\green128\blue128;
\red192\green192\blue192;}';

$colors=stripslashes($colorString);
$colors=str_replace('red', '' , $colors);
$colors=str_replace('green', ',' , $colors);
$colors=str_replace('blue', ',' , $colors);
$colors=explode(';', $colors);

// Subtract 1 from the count since the last piece is '{'
$countPieces=( count($colors)-1 );

// Set i to 1, so array piece 0 is skipped
for($i=1; $i <= $countPieces; $i++) {
preg_replace('#\\cf'.$i.'#is','<span style="color: rbg('.$colors[$i].')">',$contents);
}

jman11

5:21 am on Nov 13, 2009 (gmt 0)

10+ Year Member



after all those str_replace, and exploding, wouldn't all that would be left just like numbers, not knowing if its 2550167, or 00125, how would you know which is r, b, and g? i dont see where the array peices would be since your exploding at the ;

TheMadScientist

5:21 am on Nov 13, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member Top Contributors Of The Month



You could do the same thing with preg_match...

preg_match_all('#(\\red[0-9]{1,3}\\green[0-9]{1,3}\\blue[0-9]{1,3});#is',$contents,$new2);

// I left the ; out of the () above on purpose...
$colors=implode(';',$new2);

$colors=stripslashes($colors);
$colors=str_replace('red', '' , $colors);
$colors=str_replace('green', ',' , $colors);
$colors=str_replace('blue', ',' , $colors);
$colors=explode(';', $colors);

$countPieces=count($colors);

// Set i to 0, add one to the cf so the numbers correlate
for($i=0; $i <= $countPieces; $i++) {
preg_replace('#\\cf'.($i+1).'#is','<span style="color: rbg('.$colors[$i].')">',$contents);
}

TheMadScientist

5:32 am on Nov 13, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member Top Contributors Of The Month



after all those str_replace, and exploding, wouldn't all that would be left just like numbers, not knowing if its 2550167, or 00125, how would you know which is r, b, and g? i dont see where the array peices would be since your exploding at the ;

Remove the slashes:
red128green128blue0;red256green128blue0;

I replaced red with ''
128green128blue0;256green128blue0;

Green with ,
128,128blue0;256,128blue0;

Blue with ,
128,128,0;256,128,0;

I'm exploding on the ; so you get these as array pieces:
$piece[]='128,128,0';
$piece[]='256,128,0';

You have your comma separated RGB values...

jman11

2:58 pm on Nov 13, 2009 (gmt 0)

10+ Year Member



all the imploding and str_replace is not working at all heres what im using:


$pr = preg_match_all('/(\\\\red[0-9]{1,3}\\\\green[0-9]{1,3}\\\\blue[0-9]{1,3});/is',$contents,$new2);
// I left the ; out of the () above on purpose...
$colors=implode(';',$new2);

$colors=stripslashes($colors);
$colors=str_replace('red', '' , $colors);
$colors=str_replace('green', ',' , $colors);
$colors=str_replace('blue', ',' , $colors);
$colors=explode(';', $colors);
$countPieces=count($colors);
// Set i to 0, add one to the cf so the numbers correlate
for($i=0; $i <= $countPieces; $i++) {
$contents2 = preg_replace('/\\\cf2/is','<span style="color: rbg('.$colors[$i].')">',$contents);
}

that combination of str_replace and implode and explode and all that, leaves the $colors, in a broken array, like i cant call $colors[0] for example, and if i do print_r($colors), it does this "Array;Array" its really messed up. i tried changing it for a while but it just got more messed up.

TheMadScientist

3:11 pm on Nov 13, 2009 (gmt 0)

WebmasterWorld Senior Member 10+ Year Member Top Contributors Of The Month



<?php

$contents='{\colortbl;\red0\green0\blue0;\red0\green0\blue255;\red0\green255\blue255;
\red0\green255\blue0;\red255\green0\blue255;\red255\green0\blue0;\red255\green255\blue0;
\red255\green255\blue255;\red0\green0\blue128;\red0\green128\blue128;\red0\green128\blue0;
\red128\green0\blue128;\red128\green0\blue0;\red128\green128\blue0;\red128\green128\blue128;
\red192\green192\blue192;}';

preg_match_all('/(\\\\red[0-9]{1,3}\\\\green[0-9]{1,3}\\\\blue[0-9]{1,3});/is',$contents,$new2);
// I left the ; out of the () above on purpose...
$colors=implode('',$new2[0]);
echo '<br>';
print_r($new2[0]);
echo '<br>';
echo '<br>';
echo $colors=stripslashes($colors);
echo '<br>';
echo $colors=str_replace('red', '' , $colors);
echo '<br>';
echo $colors=str_replace('green', ',' , $colors);
echo '<br>';
echo $colors=str_replace('blue', ',' , $colors);
echo '<br>';
echo $colors=explode(';', $colors);
echo '<br>';
$countPieces=count($colors);
print_r($colors);
// Set i to 0, add one to the cf so the numbers correlate
for($i=0; $i <= $countPieces; $i++) {
$contents2 = preg_replace('/\\\cf2/is','<span style="color: rbg('.$colors[$i].')">',$contents);
}

?>

jman11

9:21 pm on Nov 13, 2009 (gmt 0)

10+ Year Member



hey i got it to work partially, but inside rgb(), its the same value for all of the replacements. heres the code im using:


preg_match_all('/(\\\\red[0-9]{1,3}\\\\green[0-9]{1,3}\\\\blue[0-9]{1,3});/is',$contents,$new2);
// I left the ; out of the () above on purpose...
$colors=implode(';',$new2);
$colors=implode('',$new2[0]);
$colors=stripslashes($colors);
$colors=str_replace('red', '' , $colors);
$colors=str_replace('green', ',' , $colors);
$colors=str_replace('blue', ',' , $colors);
$colors=explode(';', $colors);
array_unshift($colors,"");
$countPieces=count($colors)-1;
print_r($colors);
// Set i to 0, add one to the cf so the numbers correlate
for($i=1; $i<$countPieces; $i++) {
$contents2 = preg_replace('/\\\cf[1-9]+/is','<span style="color: rgb('.$colors[$i].')">',$contents);
echo $i;
}