i have a string with double quote like this
$count = 5;
$str = "result: $count";
echo $str; //result: 5
variable parsing work well, and my problem is $count var must be define later than $str
$str = "result: $count";
$count = 5;
echo $str; //result:
So i will use single quote and ask a question here to finding a way to parse var whenever i want
$str = 'result: $count';
$count = 5;
//TODO: parse var process
echo $str; //result: 5
I'm will not using regex replace.
For this type of thing, I'd probably use string formatting. In PHP, that'd be printf.
?php
$str="result: %d"
....dostuff.....define $count.....
printf($str,$count)
?
edit:
although, the best way to do this probably depends partly on why you have to define $string before $count.
If it's a string that's repeated a lot, and you wanted to put it in a global variable or something, printf would be my choice, or putting it in a function as other answers have suggested.
If the string is only used once or twice, are you sure you can't refactor the code to make $count be defined before $string?
finally, a bit of bland theory:
when you write '$string = "result: $count"',
PHP immediately takes the value of $count and puts it into the string. after that, it isn't worried about $count anymore, for purposes of $string, and even if $count changes, $string won't, because it contains a literal copy of the value.
There isn't, as far as I'm aware, a way of binding a position in a string to a yet-to-be-defined variable. The 'printf' method leaves placeholders in the string, which the function printf replaces with values when you decide what should go in the placeholders.
So, if you wanted to only write
$string = "result: $count"
$count=5
$echo string
(and not have to call another function)
and get
"result: 5",
there's no way to do that. The closest method would be using placeholders and printf, but that requires an explicit call to a function, not an implicit substitution.
Why don't you use a function?
function result_str($count) { return "result: $count"; }
preg_replace is the simplest method. Something like this:
$str = preg_replace("/\\$([a-z0-9_]+)/ie", "$\\1", $str);
But if you really don't want to use a regex, then you'll have to parse the string manually, extract the variable name, and replace it.
Related
I am programming in php and I have the following variable :
$calculation = '15-12';
Is there a function allowing me to convert the character string into calculation?
Yeah, you can use eval expression for such case, but it's not recommended (mention by #El_Vanja). It would be better to cast the values to their correct types and do the calculation.
eval scenario
$calculation = '15-12';
$result = eval('return '.$calculation.';');
print $result; // output will be 3
casted types
$calculation = '15-12';
$values = explode('-', $calculation);
$result = intval($values[0]) - intval($values[1]);
print $result;
The eval() function could be used here:
$calculation = '15-12';
$result = eval('return '.$calculation.';');
echo $result; //outputs '3'
You can use eval() https://www.php.net/manual/en/function.eval
Pay attention that this function execute the string like PHP code and if it contains specific mathematical expression, it will fail. In this case you'll need to parse your string and do calculation by yourself or use an external library.
#aspirinemaga's solution for casting is the approach that I would take.
If it isn't always going to be subtraction (and you want to avoid using eval()) then you could always use strpos to figure out if it is adding/subtracting/multiplying and then pass it the expression to a switch statement to get your calc.
With code something like this
$tk = intval($_GET['tk']);
$vosa = $_GET['vosa'];
echo $tk*100*$vosa;
Where $vosa is a string of something like 0.0425/1920*60*8. I'd need it replaced, without being calculated first, into the echo and then echo the entire thing $tk*100*0.0425/1920*60*8 result. How could I achieve this?
Ok another version. Replace the values in your string with sprintf.
echo sprintf("%s*100*%s", (string)$tk, (string)$vosa);
if %d for digit don't match your case then you can use %s. You use in your case directly $_GET variables. So sprintf is a good choice. I have tested it with:
php -r 'echo sprintf("%s*100*%s", "123", "4.000");'
output:
123*100*4.000
To output, just echo the string:
echo "{$vosa} = {$result}";
Your problem is how to calculate $result from $vosa.
A very risky way would be to use eval() - or as someone sometimes calls it, evil().
The risk is that I could send you a vosa value of system('FORMAT C: /AUTOTEST') (which would not work, but you get my meaning).
// vosa='/bin/dd if=/dev/zero of=etc etc'
// This will return zero. It will return a whole lot of zeroes
// all over your hard disk.
$result = eval("return {$tk}*100*{$vosa};");
Possibly, validating $vosa with a regular expression could help, at least as long as you use simple expressions.
Alternately, you must implement an expression parser.
This is another ready made. You would use it like this:
include('./some/where/mathparser.php');
$parser = new MathParser();
$parser->setExpression("{$tk}*100*{$vosa}");
$result = $parser->getValue();
echo "The result of {$tk}*100*{$vosa} is {$result}.";
You can use string and then use eval to execute it as a php code:
<?php
$tk = intval($_GET['tk']);
$vosa = $_GET['vosa'];
echo eval("return $tk*100*$vosa;");
Caution
The eval() language construct is very dangerous because it allows execution of arbitrary PHP code. Its use thus is discouraged. If you have carefully verified that there is no other option than to use this construct, pay special attention not to pass any user provided data into it without properly validating it beforehand.
$tk = intval($_GET['tk']);
$vosa = $_GET['vosa']; // "0.0425/1920*60*8"
$ans = eval('return '.$vosa.';');
echo $ans;
echo "<br>";
echo $tk*100*$ans;
Example : https://eval.in/819834
Got it myself
<?php
$tk = $_GET['tk'];
$aeg = $_GET['aeg'];
$kfc = $_GET['kfc'];
$vosa = $_GET['vosa'];
$final = $tk.'*'.$aeg.'*'.$kfc.'*'.$vosa;
$ans = eval('return '.$final.';');
echo round($ans,2);
Weird situation and I'm not even sure what to call it (hence unable to find any previous posts).
I'm passing in a variable that is a string as function, and then attempting to concat it to another string as such:
function saveFunction($number){
$myStr = "drawer-$number[]";
return $myStr;
}
So the output should be :
saveFunction("2")
"drawer-2[]"
However, because it thinks I am accessing $number as an array because of the brackets, the output is:
"0"
I even tried this:
function saveFunction($number){
$myStr = "drawer-$number";
return $myStr + "[]";
}
And got the same result.
Suggestions?
Double quotes in PHP are tricky. They interpret the string. This is why "drawing-$number" works in the first place.
Sometimes your string doesn't lend itself for automatic interpretation. You can use the always safe concatenation:
return "drawer-" . $number . "[]";
Or use {} to help the automatic detection:
return "drawer-{$number}[]"; // as opposed to: "drawer-{$number[]}"
Or use sprintf:
return sprintf("drawer-%s[]", $number); // %s because $number is actually a string, not an int
You can just concat the variable with the string like this:
<?php
function saveFunction($number){
return $myStr = "drawer-" . $number . "[]";
}
echo saveFunction("2");
?>
Output:
drawer-2[]
For further information see also: http://php.net/manual/en/language.operators.string.php
I'm storing some strings within a *.properties file. An example of a string is:
sendingFrom=Sending emails from {$oEmails->agentName}, to {$oEmails->customerCount} people.
My function takes the value from sendingFrom and then outputs that string on the page, however it doesn't automatically parse the {$oEmails->agentName} within. Is there a way, without manually parsing that, for me to get PHP to convert the variable from a string, into what it should be?
If you can modify your *.properties, here is a simple solution:
# in file.properties
sendingFrom = Sending emails from %s, to %s people.
And then replacing %s with the correct values, using sprintf:
// Get the sendingFrom value from file.properties to $sending_from, and:
$full_string = sprintf($sending_from, $oEmails->agentName, $oEmails->customerCount);
It allows you to separate the logic of your app (the variables, and how you get them) from your presentation (the actual string scheme, stored in file.properties).
Just an alternative.
$oEmails = new Emails('Me',4);
$str = 'sendingFrom=Sending emails from {$oEmails->agentName}, to {$oEmails->customerCount} people.';
// --------------
$arr = preg_split('~(\{.+?\})~',$str,-1,PREG_SPLIT_DELIM_CAPTURE);
for ($i = 1; $i < count($arr); $i+=2) {
$arr[$i] = eval('return '.substr($arr[$i],1,-1).';');
}
$str = implode('',$arr);
echo $str;
// sendingFrom=Sending emails from Me, to 4 people.
as others mentioned eval wouldn't be appropriate, I suggest a preg_replace or a preg_replace_callback if you need more flexibility.
preg_replace_callback('/\$(.+)/', function($m) {
// initialise the data variable from your object
return $data[$m[1]];
}, $subject);
Check this link out as well, it suggests the use of strstr How replace variable in string with value in php?
You can use Eval with all the usual security caviats
Something like.
$string = getStringFromFile('sendingFrom');
$FilledIn = eval($string);
join_strings(string $glue, string $var, string $var2 [, string $...]);
I am looking for something that would behave similar to the function I conceptualized above. A functional example would be:
$title = "Mr.";
$fname = "Jonathan";
$lname = "Sampson";
print join_strings(" ", $title, $fname, $lname); // Mr. Jonathan Sampson
After giving the documentation a quick look-over, I didn't see anything that does this. The closest I can think of is implode(), which operates on arrays - so I would have to first add the strings into an array, and then implode.
Is there already a method that exists to accomplish this, or would I need to author one from scratch?
Note: I'm familiar with concatenation (.), and building-concatenation (.=). I'm not wanting to do that (that would take place within the function). My intentions are to write the $glue variable only once. Not several times with each concatenation.
you can use join or implode, both do same thing
and as you say it needs to be an array which is not difficult
join($glue, array($va1, $var2, $var3));
You can use func_get_args() to make implode() (or its alias join()) bend to your will:
function join_strings($glue) {
$args = func_get_args();
array_shift($args);
return implode($glue, $args);
}
As the documentation for func_get_args() notes, however:
Returns an array in which each element is a copy of the corresponding member of the current user-defined function's argument list.
So you still end up making an array out of the arguments and then passing it on, except now you're letting PHP take care of that for you.
Do you have a more convincing example than the one in your question to justify not simply using implode() directly?
The only thing you're doing now is saving yourself the trouble to type array() around the variables, but that's actually shorter than the _strings you appended to the function name.
Try this:
function join_strings($glue, $arg){
$args = func_get_args();
$result = "";
$argcount = count($args)
for($i = 1; $i < $argcount; $i++){
$result .= $args[$i];
if($i+1!=count($args){
$result .= $glue;
}
}
return $result;
}
EDIT: Improved function thanks to comment suggestion
$a="hi";
$b = " world";
echo $a.$b;
While I agree with the accepted answer, see this article thats says implode is faster than join.
You'll have to use the dot "." operator.
This comes from abstract algebra theory, the strings being a monoid with respect to the concatenation operator, and the fact that when dealing with algebraic structures the dot is usually used as a generic operator (the other being "+", which you may have seen used in other languages).
For quick reference, being a monoid implies associativity of the operation, and that there exists an identity element (the empty string, in our case).