Add a space on a string but counting right to left - php

Iv seeing some answers like: Add space after every 4th character using
echo wordwrap('1234567890' , 4 , '-' , true )
But in this case I need to count the characters from right to left.
For example to format a phone number user friendly 123-123-1234. The problem is that sometimes the user could submit a code area, and If I start normally left to right I can get this: 012-312-3123-4 So I am thinking of starting right to left.
Any ideas?

A regex with a lookahead assertion that there are one or more groups of 4 characters between the matched position and the end of the string should do this for you.
echo preg_replace("/(?=(.{4})+$)/", "-", "1234567890");
// 12-3456-7890
You'll need to handle strings with an exact multiple of 4 characters which will end up with a hyphen at the beginning. You could either add a lookbehind assertion to the regex or it might be easier to read if you trim the hyphen off afterwards.
echo preg_replace("/(?=(.{4})+$)/", "-", "123456789012");
// -1234-5678-9012
echo preg_replace("/(?<=.)(?=(.{4})+$)/", "-", "123456789012");
// 1234-5678-9012
echo ltrim(preg_replace("/(?=(.{4})+$)/", "-", "123456789012"), "-");
// 1234-5678-9012

This works
function myFormat($s, $len, $delimiter = "-")
{
$techChar = " ";
$newLen = ceil(strlen($s) / $len) * $len;
$s = str_pad($s, $newLen, $techChar, STR_PAD_LEFT);
$s = wordwrap($s, $len, $delimiter, true);
$s = ltrim($s, $techChar);
return $s;
}

Related

Remove s or 's from all words in a string with PHP

I have a string in PHP
$string = "Dogs are Jonny's favorite pet";
I want to use regex or some method to remove s or 's from the end of all words in the string.
The desired output would be:
$revisedString = "Dog are Jonny favorite pet";
Here is my current approach:
<?php
$string = "Dogs are Jonny's favorite pet";
$stringWords = explode(" ", $string);
$counter = 0;
foreach($stringWords as $string) {
if(substr($string, -1) == s){
$stringWords[$counter] = trim($string, "s");
}
if(strpos($string, "'s") !== false){
$stringWords[$counter] = trim($string, "'s");
}
$counter = $counter + 1;
}
print_r($stringWords);
$newString = "";
foreach($stringWords as $string){
$newString = $newString . $string . " ";
}
echo $newString;
}
?>
How would this be achieved with REGEX?
For general use, you must leverage much more sophisticated technique than an English-ignorant regex pattern. There may be fringe cases where the following pattern fails by removing an s that it shouldn't. It could be a name, an acronym, or something else.
As an unreliable solution, you can optionally match an apostrophe then match a literal s if it is not immediately preceded by another s. Adding a word boundary (\b) on the end improves the accuracy that you are matching the end of words.
Code: (Demo)
$string = "The bass can access the river's delta from the ocean. The fishermen, assassins, and their friends are happy on the banks";
var_export(preg_replace("~'?(?<!s)s\b~", '', $string));
Output:
'The bass can access the river delta from the ocean. The fishermen, assassin, and their friend are happy on the bank'
PHP Live Regex always helped me a lot in such moments. Even already knowing how REGEX works, I still use it just to be sure some times.
To make use of REGEX in your case, you can use preg_replace().
<?php
// Your string.
$string = "Dogs are Jonny's favorite pet";
// The vertical bar means "or" and the backslash
// before the apostrophe is needed so you don't end
// your pattern string since we're using single quotes
// to delimit it. "\s" means a single space.
$regex_pattern = '/\'s\s|s\s|s$/';
// Fill the preg_replace() with the pattern, the replacement
// (a single space in this case), your string, -1 (so preg_replace()
// will replace all the matches) and a variable of your desire
// to be the "counter" (preg_replace() will automatically
// fill it).
$newString = preg_replace($regex_pattern, ' ', $string, -1, $counter);
// Use the rtrim() to remove spaces at the right of the sentence.
$newString = rtrim($newString, " ");
echo "New string: " . $newString . ". ";
echo "Replacements: " . $counter . ".";
?>
In this case, the function will identify any "'s" or "s" with spaces (\s) after them and then replace them with a single space.
The preg_replace() will also count all the replacements and register them automatically on $counter or any variable you place there instead.
Edit:
Phil's comment is right and indeed my previous REGEX would lose a "s" at the end of the string. Adding "|s$" will solve it. Again, "|" means "or" and the "$" means that the "s" must be at the end of the string.
In attention to mickmackusa's comment, my solution is meant only to remove "s" characters at the end of words inside the string as this was Sparky Johnson' request here. Removing plurals would require a complex code since not only we need to remove "s" characters from plural only words but also change verbs and other stuff.

php regex replace each character with asterisk

I am trying to something like this.
Hiding users except for first 3 characters.
EX)
apple -> app**
google -> goo***
abc12345 ->abc*****
I am currently using php like this:
$string = "abcd1234";
$regex = '/(?<=^(.{3}))(.*)$/';
$replacement = '*';
$changed = preg_replace($regex,$replacement,$string);
echo $changed;
and the result be like:
abc*
But I want to make a replacement to every single character except for first 3 - like:
abc*****
How should I do?
Don't use regex, use substr_replace:
$var = "abcdef";
$charToKeep = 3;
echo strlen($var) > $charToKeep ? substr_replace($var, str_repeat ( '*' , strlen($var) - $charToKeep), $charToKeep) : $var;
Keep in mind that regex are good for matching patterns in string, but there is a lot of functions already designed for string manipulation.
Will output:
abc***
Try this function. You can specify how much chars should be visible and which character should be used as mask:
$string = "abcd1234";
echo hideCharacters($string, 3, "*");
function hideCharacters($string, $visibleCharactersCount, $mask)
{
if(strlen($string) < $visibleCharactersCount)
return $string;
$part = substr($string, 0, $visibleCharactersCount);
return str_pad($part, strlen($string), $mask, STR_PAD_RIGHT);
}
Output:
abc*****
Your regex matches all symbols after the first 3, thus, you replace them with a one hard-coded *.
You can use
'~(^.{3}|(?!^)\G)\K.~'
And replace with *. See the regex demo
This regex matches the first 3 characters (with ^.{3}) or the end of the previous successful match or start of the string (with (?!^)\G), and then omits the characters matched from the match value (with \K) and matches any character but a newline with ..
See IDEONE demo
$re = '~(^.{3}|(?!^)\G)\K.~';
$strs = array("aa","apple", "google", "abc12345", "asdddd");
foreach ($strs as $s) {
$result = preg_replace($re, "*", $s);
echo $result . PHP_EOL;
}
Another possible solution is to concatenate the first three characters with a string of * repeated the correct number of times:
$text = substr($string, 0, 3).str_repeat('*', max(0, strlen($string) - 3));
The usage of max() is needed to avoid str_repeat() issue a warning when it receives a negative argument. This situation happens when the length of $string is less than 3.

PHP - How can i get specific number of characters after last occurence of a character in a string

This is the string http://www.sportsdirect.com/adidas-pure-360-mens-golf-shoes-283042?colcode=28304201
How can i get the first SIX characters after the last occurence of - ?
Thanks in advance!
Plenty of ways to skin the cat on this one.
Here's one of them:
$url = 'http://www.sportsdirect.com/adidas-pure-360-mens-golf-shoes-283042?colcode=28304201';
preg_match('/-(\d+)\?/', $url, $result);
var_dump($result[1]); // string(6) "283042"
The pattern says "match at least one consecutive number that lies between a dash and a question mark".
Find the last occurrence of - with strrpos then grab the 6 characters after it with substr
Example:
$string = "http://www.sportsdirect.com/adidas-pure-360-mens-golf-shoes-283042?colcode=28304201";
echo substr(
$string,
strrpos($string, "-") + 1,
6
);
Output:
283042
try this may help
<?php
$str = "http://www.sportsdirect.com/adidas-pure-360-mens-golf-shoes-283042?colcode=28304201";
$at = strtok($str, "?");
if ($at) {
$sixltr = substr($at, -6);
echo $sixltr;
}
?>
$link = "http://www.sportsdirect.com/adidas-pure-360-mens-golf-shoes-283042?colcode=28304201";
if(strrpos($link, '-')){ // check if "-" is exist
echo substr($link,strrpos($link, '-')+1,6);
}
strrpos - Finds the position of the last occurrence of a string inside another string

Put something after the nth digit, rather than nth character?

I'm working on an autocomplete for SSN-like numbers in PHP. So if the user searches for '123', it should find the number 444123555. I want to bold the results, thus, 444<b>123</b>555. I then, however, want to format it as an SSN - thus creating 444-<b>12-3</b>555.
Is there some way to say 'put the dash after the nth digit'? Because I don't want the nth character, just the nth digit - if I could say 'put a dash after the third digit and the fifth digit, ignoring non-numeric characters like <, b, and >' that would be awesome. Is this doable in a regex?
Or is there a different method that's escaping me here?
Just iterate over the string and check that each character is a digit and count the digits as you go.
That will be so much faster than regex, even if regex were a feasible solution here (which I am not convinced it is).
This will do exactly what you asked for:
$str = preg_replace('/^ ((?:\D*\d){3}) ((?:\D*\d){2}) /x', '$1-$2-', $str);
The (?:\D*\d) Will match any number of non-digits, then a digit. By repeating that n times, you match n digits, "ignoring" everything else.
Here's a simple function using an iterative approach as Platinum Azure suggests:
function addNumberSeparator($numString, $n, $separator = '-')
{
$numStringLen = strlen($numString);
$numCount = 0;
for($i = 0; $i < $numStringLen; $i++)
{
if(is_numeric($numString[$i]))
{
$numCount++;
//echo $numCount . '-' . $i;
}
if($numCount == $n)
return substr($numString, 0, $i + 1) . $separator . substr($numString, $i + 1);
}
}
$string = '444<b>123</b>555';
$string = addNumberSeparator($string, 3);
$string = addNumberSeparator($string, 5);
echo $string;
This outputs the following:
4x<b>x123</b>555
That will, of course, only work with a non-numeric separator character. Not the most polished piece of code, but it should give you a start!
Hope that helps.
If you want to get formated number and surrounding text:
<?php
preg_match("/(.*)(\d{3})(12)(3)(.*)/", "assd444123666as555", $match);
$str = $match[1];
if($match[2]!=="") $str.=$match[2]."-<b>";
$str.=$match[3]."-".$match[4]."</b>";
if($match[5]!=="") $str.=$match[5];
echo $str;
?>
If only formatted number:
<?php
preg_match("/(.*)(\d{3})(12)(3)(.*)/", "as444123666as555", $match);
$str = "";
if($match[2]!=="") $str.=$match[2]."-<b>";
$str.=$match[3]."-".$match[4]."</b>";
echo $str;
?>
Sorry, but it is a bit ambiguous.

Auto-link URLs in a string

I have a normal message output $msg. I want it to make it links, if it is links. (containing http:// or www.) then it should make it http://google.com
I have stripped html from the messages
$msg = htmlspecialchars(strip_tags($show["status"]), ENT_QUOTES, 'utf-8')
How can that be done, seen it many places.
I had the same problem like #SublymeRick (stops after first dot, see Auto-link URLs in a string).
With a little inspiration from https://stackoverflow.com/a/8218223/593957 I changed it to
$msg = preg_replace('/((http|ftp|https):\/\/[\w-]+(\.[\w-]+)+([\w.,#?^=%&:\/~+#-]*[\w#?^=%&\/~+#-])?)/', '\1', $msg);
Use a regular expression for this, via PHP's preg_replace() function.
Something like this....
preg_replace('/\b(https?:\/\/(.+?))\b/', '\1', $text);
Explaination:
Looks for (https?://(.+?)) surrounded by \b, which is a beginning-of-word / end-of-word marker.
https?:// is obvious (the s? means that the 's' is optional).
(.+?) means any number of any characters: 'any character' is represented by the dot; 'any number of' is the plus sign. The question mark means it isn't greedy, so it will allow the item after it (ie the \b end of word) to match at the first opportunity. This stops it just carrying on till the end of the string.
The whole expression is in brackets so that it gets picked up the the replacement system and can be re-inserted using \1 in the second parameter.
Something like:
preg_replace('#(https?://([-\w\.]+)+(:\d+)?(/([\w/_\.]*(\?\S+)?)?)?)#', '$1', $text);
maybe?
enter code h function AutoLinkUrls($str,$popup = FALSE){
if (preg_match_all("#(^|\s|\()((http(s?)://)|(www\.))(\w+[^\s\)\<]+)#i", $str, $matches)){
$pop = ($popup == TRUE) ? " target=\"_blank\" " : "";
for ($i = 0; $i < count($matches['0']); $i++){
$period = '';
if (preg_match("|\.$|", $matches['6'][$i])){
$period = '.';
$matches['6'][$i] = substr($matches['6'][$i], 0, -1);
}
$str = str_replace($matches['0'][$i],
$matches['1'][$i].'<a href="http'.
$matches['4'][$i].'://'.
$matches['5'][$i].
$matches['6'][$i].'"'.$pop.'>http'.
$matches['4'][$i].'://'.
$matches['5'][$i].
$matches['6'][$i].'</a>'.
$period, $str);
}//end for
}//end if
return $str;
}//end AutoLinkUrlsere

Categories