php preg_match problem - php

how can i get 41P86246HOH7C1G4A983321910HDL63U9 from the following with preg_match
input type="text" value="41P86246HOH7C1G4A983321910HDL63U9" id=""

DOMDocument::loadHTML("<$input>")->getElementsByTagName('input')
->item(0)->getAttribute('value');

What about something like this :
$str = 'input type="text" value="41P86246HOH7C1G4A983321910HDL63U9" id=""';
$m = array();
if (preg_match('#value="([^"]+)"#', $str, $m)) {
var_dump($m[1]);
}
Which will match everything between the double quotes that come with value, and get you :
string '41P86246HOH7C1G4A983321910HDL63U9' (length=33)
But, as a sidenote : if you are trying to "parse" HTML with regex, it's generally not the "best" way ; HTML is not quite regular enough for regex...

Simply, without extra characters:
preg_match('/(?<=value=")[0-9A-Za-z]+/', $str, $match);
Your result is in $match[0];

With something like this:
if(preg_match('#value="([^"]*)"#', $text, $m)){
echo $m[1];
}
But you can also make something who split the string in each key with this value.
function attributes($text){
$attrs = array();
if(preg_match_all('#(\b[^=]*\b)\s*=\s*"([^"]+)"#', $text, $matches, PREG_SET_ORDER)){
foreach($matches as $m){
$attrs[$m[1]] = $m[2];
}
}
return $attrs;
}
// Use like this
$attrs = attributes('input value="bla"');
if(isset($attrs['value'])){
echo $attrs['value'];
}

don't even have to use regex. Just use PHP's string methods
$str='input type="text" value="41P86246HOH7C1G4A983321910HDL63U9" id=""';
$s = explode(" ",$str);
// go through each element, find "value"
foreach($s as $a=>$b){
if(strpos($b,"value")!==FALSE){
$find = explode("=",$b);
print $find[1];
}
}

Related

replacing letters with numbers

So i've been trying to get this bit of code to work all day and haven't been able to do it... I wnat to be able to replace letters with a number (or just a value) from an array. this is the code i've got:
$l2n =
array(
'a'=>'1',
'b'=>'2',
'c'=>'3',
'd'=>'4',
'e'=>'5',
'f'=>6,
'g'=>7,
'h'=>8,
'i'=>9,
'j'=>10,
'k'=>11,
'l'=>12,
'm'=>13,
'n'=>14,
'o'=>15,
'p'=>16,
'q'=>17,
'r'=>18,
's'=>19,
't'=>20,
'u'=>21,
'v'=>22,
'w'=>23,
'x'=>24,
'y'=>25,
'z'=>16
);
$string = str_split($string);
$explode = array_shift($string);
if($l2n[$explode] == $explode)
{
echo $l2n[$explode];
}
else
{
echo $l2n['a'];
}
I tried to use Preg_replace but i've never had a good expereince with that function. so If anybody could help me out, hint me in the correct direction, that'd be great.
You can just use str_replace once you've used array_keys and array_values to get each side of the array:
$keys = array_keys($l2n);
$values = array_values($l2n);
$yourstring = 'Hello world!';
echo str_replace($keys, $values, $yourstring);
// H5121215 231518124!
Demo: https://eval.in/77453
Docs:
http://php.net/str_replace
http://php.net/array_keys
http://php.net/array_values
You can simply do:
$string = preg_replace(array_keys($l2n), array_values($l2n), $string);
From the documentation:
If both pattern and replacement parameters are arrays, each pattern will be replaced by the replacement counterpart.
Why in the world would you use an array for this? Isn't ord() what you are looking for here?
$string = "ABCDE";
foreach ( str_split($string) as $chr ) {
echo ord($chr) - 64; // or 97 if they all are lowercase
echo PHP_EOL;
}

Regex to transform abcd to (a(b(c(d))))

I'm using PHP's preg_replace, and trying to transform the string
abcd
into
(a(b(c(d))))
This is the best I've got:
preg_replace('/.(?=(.*$))/', '$0($1)', 'abcd');
// a(bcd)b(cd)c(d)d()
Is it even possible with regex?
Edit I've just discovered this in the PCRE spec: Replacements are not subject to re-matching, so my original approach isn't going to work. I wanted to keep it all regex because there's some more complicated matching logic in my actual use case.
How about:
preg_replace('/./s', '($0', 'abcd') . str_repeat(')', strlen('abcd'));
?
(Does that count as "with regex"?)
You can use preg_match_all. Not sure what kind of characters you want, though. So I'll give an example for all characters:
$val = 'abcd1234';
$out = '';
if(preg_match_all('#.#', $val, $matches))
{
$i = 0; // we'll use this to keep track of how many open paranthesis' we have
foreach($matches[0] as &$v)
{
$out .= '('.$v;
$i++;
}
$out .= str_repeat(")", $i);
}
else
{
// no matches found or error occured
}
echo $out; // (a(b(c(d(1(2(3(4))))))))
Will be easy to customise further, as well.
This is my way to do it =) :
<?php
$arr = str_split("abcd");
$new_arr = array_reverse($arr);
foreach ($new_arr as $a) {
$str = sprintf('(%s%s)', $a, $str);
}
echo "$str\n";
?>
KISS isn't it ? (few lines : 6)
I went with something along the lines of a combination of the above answers:
preg_match_all('/./ui', 'abcd', $matches);
$matches = $matches[0];
$string = '('.implode('(', $matches).str_repeat(')', count($matches));

PHP Extract numbers from a string

I want to extract numbers from a string in PHP like following :
if the string = 'make1to6' i would like to extract the numeric character before and after the 'to' substring in the entire string. i.e. 1 and 6 are to be extracted
i will be using these returned values for some calculations.' i would like to extract the numeric character before and after the 'to' substring in the entire string. i.e. 1 and 6 are to be extracted
The length of the string is not fixed and can be a max of 10 characters in length.The number can be of max two digits on either side of 'to' in the string.
Some example string values :
sure1to3
ic3to9ltd
anna1to6
joy1to4val
make6to12
ext12to36
thinking of something like :
function beforeTo(string) {
return numeric_value_before_'to'_in_the_string;
}
function afterTo(string) {
return numeric_value_after_'to'_in_the_string;
}
i will be using these returned values for some calculations.
You could use preg_match_all to achive this:
function getNumbersFromString($str) {
$matches = array();
preg_match_all('/([0-9]+)/', $str, $matches);
return $matches;
}
$matches = getNumbersFromString('hej 12jippi77');
Use preg_match with a regex that will extract the numbers for you. Something like this should do the trick for you:
$matches = null;
$returnValue = preg_match('/([\d+])to([\d+])/uis', 'ic3to9ltd', $matches);
After this $matches will look like:
array (
0 => '3to9',
1 => '3',
2 => '9',
);
You should read somewhat on regular expressions, it's not hard to do stuff like this if you know how they work. Will make your life easier. ;-)
You can use a regular expression as such, it should match exactly your specification:
$string = 'make6to12';
preg_match('{^.*?(?P<before>\d{1,2})to(?P<after>\d{1,2})}m', $string, $match);
echo $match['before'].', '.$match['after']; // 6, 12
You can use this:
// $str holds the string in question
if (preg_match('/(\d+)to(\d+)/', $str, $matches)) {
$number1 = $matches[1];
$number2 = $matches[2];
}
You can use regular expressions.
$string = 'make1to6';
if (preg_match('/(\d{1,10})to(\d{1,10})/', $string, $matches)) {
$number1 = (int) $matches[1];
$number2 = (int) $matches[2];
} else {
// Not found...
}
<?php
$data = <<<EOF
sure1to3
ic3to9ltd
anna1to6
joy1to4val
make6to12
ext12to36
EOF;
preg_match_all('#(\d+)to(\d+)#s', $data, $matches);
header('Content-Type: text/plain');
//print_r($matches);
foreach($matches as $match)
{
echo sprintf("%d, %d\n", $match[1], $match[2]);
}
?>
This is what Regular Expressions are for - you can match multiple instances of very specific patterns and have them returned to you in an array. It's pretty awesome, truth be told :)
Take a look here for how to use the built in regular expression methods in php : LINK
And here is a fantastic tool for testing regular expressions: LINK
<?php
list($before, $after) = explode('to', 'sure1to3');
$before_to = extract_ints($before);
$after_to = extract_ints($after);
function extract_ints($string) {
$ints = array();
$len = strlen($string);
for($i=0; $i < $len; $i++) {
$char = $string{$i};
if(is_numeric($char)) {
$ints[] = intval($char);
}
}
return $ints;
}
?>
A regex seems really unnecessary here since all you are doing is checking is_numeric() against a bunch of characters.

mb_eregi_replace multiple matches get them

$string = 'test check one two test3';
$result = mb_eregi_replace ( 'test|test2|test3' , '<$1>' ,$string ,'i');
echo $result;
This should deliver: <test> check one two <test3>
Is it possible to get, that test and test3 was found, without using another match function ?
You can use preg_replace_callback instead:
$string = 'test check one two test3';
$matches = array();
$result = preg_replace_callback('/test|test2|test3/i' , function($match) use ($matches) {
$matches[] = $match;
return '<'.$match[0].'>';
}, $string);
echo $result;
Here preg_replace_callback will call the passed callback function for each match of the pattern (note that its syntax differs from POSIX). In this case the callback function is an anonymous function that adds the match to the $matches array and returns the substitution string that the matches are to be replaced by.
Another approach would be to use preg_split to split the string at the matched delimiters while also capturing the delimiters:
$parts = preg_split('/test|test2|test3/i', $string, null, PREG_SPLIT_DELIM_CAPTURE);
The result is an array of alternating non-matching and matching parts.
As far as I know, eregi is deprecated.
You could do something like this:
<?php
$str = 'test check one two test3';
$to_match = array("test", "test2", "test3");
$rep = array();
foreach($to_match as $val){
$rep[$val] = "<$val>";
}
echo strtr($str, $rep);
?>
This too allows you to easily add more strings to replace.
Hi following function used to found the any word from string
<?php
function searchword($string, $words)
{
$matchFound = count($words);// use tha no of word you want to search
$tempMatch = 0;
foreach ( $words as $word )
{
preg_match('/'.$word.'/',$string,$matches);
//print_r($matches);
if(!empty($matches))
{
$tempMatch++;
}
}
if($tempMatch==$matchFound)
{
return "found";
}
else
{
return "notFound";
}
}
$string = "test check one two test3";
/*** an array of words to highlight ***/
$words = array('test', 'test3');
$string = searchword($string, $words);
echo $string;
?>
If your string is utf-8, you could use preg_replace instead
$string = 'test check one two test3';
$result = preg_replace('/(test3)|(test2)|(test)/ui' , '<$1>' ,$string);
echo $result;
Oviously with this kind of data to match the result will be suboptimal
<test> check one two <test>3
You'll need a longer approach than a direct search and replace with regular expressions (surely if your patterns are prefixes of other patterns)
To begin with, the code you want to enhance does not seem to comply with its initial purpose (not at least in my computer). You can try something like this:
$string = 'test check one two test3';
$result = mb_eregi_replace('(test|test2|test3)', '<\1>', $string);
echo $result;
I've removed the i flag (which of course makes little sense here). Still, you'd still need to make the expression greedy.
As for the original question, here's a little proof of concept:
function replace($match){
$GLOBALS['matches'][] = $match;
return "<$match>";
}
$string = 'test check one two test3';
$matches = array();
$result = mb_eregi_replace('(test|test2|test3)', 'replace(\'\1\')', $string, 'e');
var_dump($result, $matches);
Please note this code is horrible and potentially insecure. I'd honestly go with the preg_replace_callback() solution proposed by Gumbo.

Parsing a Source With REGEX

I want to get all Performance ID's from this page .
<?php
$content = file_get_contents("http://www124.popmundo.com/Common/Performances.asp?action=ComingPerformances&ArtistID=1962457");
$regex = "Performances\.asp\?action=Arrangements&PerformanceID=([0-9]+)";
//$regex = "/Performances\.asp\?action=Arrangements&PerformanceID=([0-9]+)/";
//$regex = "/Performances\.asp\?action=Arrangements&PerformanceID=([0-9]+)/s";
//all pattern variations tested, not working
if(preg_match_all($regex, $content, $m))
print_r($m);
else
echo "FALSE";
// this is returning FALSE
Use & instead of & in your regex.
Try this:
$regex = "/Performances\.asp\?action=Arrangements&PerformanceID=([0-9]+)/";
It looks like an escape problem. Not knowing php, I would guess one of these
might fix it:
$regex = 'Performances\.asp\?action=Arrangements&PerformanceID=([0-9]+)';
or
$regex = "Performances\\.asp\\?action=Arrangements&PerformanceID=([0-9]+)";
or
$regex = '/Performances\.asp\?action=Arrangements&PerformanceID=([0-9]+)/';

Categories