Does anybody have the exact name of the function Drupal uses to turn the following string:
"Hello, how are you. Some more text."
into
"Hello, how..."
I.e. The function that's used to cut off a sentence after x words, and then add an elipsis. Alternatively, if anybody has a php snippet that does this, that would be great too!
function getFirstWords($string, $words = 1)
{
$string = explode(' ', $string);
if (count($string) > $words)
{
return implode(' ', array_slice($string, 0, $words)) . '...';
}
return implode(' ', $string);
}
echo getFirstWords('Hello, how are you. Some more text.', 2); // Hello, how...
It seems to be truncate_utf8() in unicode.inc.
You can use function views_trim_text($alter, $value)
view more detail https://api.drupal.org/api/views/views.module/function/views_trim_text/7
$alter['html'] = TRUE;
$alter['max_length'] = 200;
$alter['word_boundary'] = TRUE;
$alter['ellipsis'] = TRUE;
print views_trim_text($alter, $output);
Related
I'm trying to lowercase every character in a string except for the last one that should be in uppercase.
Here is my code:
function caps_caps($var) {
$var = strrev(ucwords(strrev($var)));
echo $var;
}
caps_caps("HeLlo WOrld"); // should returns "hellO worlD"
This is the easy solution of this problem
function caps_caps($var) {
$var = strrev(ucwords(strrev(strtolower($var))));
echo $var;
}
caps_caps("HeLlo WOrld");
Demo
You also need to convert the string to lowercase first.
function caps_caps($var) {
$var = strrev(ucwords(strrev(strtolower($var))));
echo $var;
}
caps_caps("HeLlo WOrld"); // returns "hellO worlD"
function caps_caps($text) {
$value_to_print = '';
$text = strrev(ucwords(strrev($text)));
$words = explode(' ', $text);
foreach($words as $word){
$word = strtolower($word);
$word[strlen($word)-1] = strtoupper($word[strlen($word)-1]);
$value_to_print .= $word . ' ';
}
echo trim($value_to_print);
}
caps_caps("HeLlo WOrld");
You can try this piece of code.
function uclast($s)
{
$lastCharacterUppar = '';
if ( preg_match('/\s/',$s) ){//If string has space
$explode = explode(' ',$s);
for($i=0;$i<count($explode);$i++){
$l=strlen($explode[$i])-1;
$explode[$i] = strtolower($explode[$i]);
$explode[$i][$l] = strtoupper($explode[$i][$l]);
}
$lastCharacterUppar = implode(' ', $explode);
} else { //if string without space
$l=strlen($s)-1;
$s = strtolower($s);
$s[$l] = strtoupper($s[$l]);
$lastCharacterUppar = $s;
}
return $lastCharacterUppar;
}
$str = 'hey you yo';
echo uclast($str);
Try this, you forgot to do foreach, each elements.
function uclast_words($text, $delimiter = " "){
foreach(explode($delimiter, $text) as $value){
$temp[] = strrev(ucfirst(strrev(strtolower($value))));
}
return implode($delimiter, $temp);
}
print_r(uclast_words("hello world", " "));
I hope this is the answer of your question.
Here is a multibyte safe technique that performs the title-casing with one call instead of two. The string reversal and re-reversal is still necessary.
Code: (Demo)
echo strrev(
mb_convert_case(
strrev('HeLlo WOrld'),
MB_CASE_TITLE
)
);
// hellO worlD
I am using regular expression for getting multiple patterns from a given string.
Here, I will explain you clearly.
$string = "about us";
$newtag = preg_replace("/ /", "_", $string);
print_r($newtag);
The above is my code.
Here, i am finding the space in a word and replacing the space with the special character what ever i need, right??
Now, I need a regular expression that gives me patterns like
about_us, about-us, aboutus as output if i give about us as input.
Is this possible to do.
Please help me in that.
Thanks in advance!
And finally, my answer is
$string = "contact_us";
$a = array('-','_',' ');
foreach($a as $b){
if(strpos($string,$b)){
$separators = array('-','_','',' ');
$outputs = array();
foreach ($separators as $sep) {
$outputs[] = preg_replace("/".$b."/", $sep, $string);
}
print_r($outputs);
}
}
exit;
You need to do a loop to handle multiple possible outputs :
$separators = array('-','_','');
$string = "about us";
$outputs = array();
foreach ($separators as $sep) {
$outputs[] = preg_replace("/ /", $sep, $string);
}
print_r($outputs);
You can try without regex:
$string = 'about us';
$specialChar = '-'; // or any other
$newtag = implode($specialChar, explode(' ', $string));
If you put special characters into an array:
$specialChars = array('_', '-', '');
$newtags = array();
foreach ($specialChars as $specialChar) {
$newtags[] = implode($specialChar, explode(' ', $string));
}
Also you can use just str_replace()
foreach ($specialChars as $specialChar) {
$newtags[] = str_replace(' ', $specialChar, $string);
}
Not knowing exactly what you want to do I expect that you might want to replace any occurrence of a non-word (1 or more times) with a single dash.
e.g.
preg_replace('/\W+/', '-', $string);
If you just want to replace the space, use \s
<?php
$string = "about us";
$replacewith = "_";
$newtag = preg_replace("/\s/", $replacewith, $string);
print_r($newtag);
?>
I am not sure that regexes are the good tool for that. However you can simply define this kind of function:
function rep($str) {
return array( strtr($str, ' ', '_'),
strtr($str, ' ', '-'),
str_replace(' ', '', $str) );
}
$result = rep('about us');
print_r($result);
Matches any character that is not a word character
$string = "about us";
$newtag = preg_replace("/(\W)/g", "_", $string);
print_r($newtag);
in case its just that... you would get problems if it's a longer string :)
I am trying to find the word and add a number next to it. How could he do? I tried with the code below, but I could not. Could anyone help me?
Thank you!
$string = 'I220ABCD I220ABCDEF I220ABCDEFG'
if (preg_match("/I220.*/", $string, $matches)) {
echo $matches[0];
}
Expected result:
I220ABCD9
I220ABCDEF10
I220ABCDEFG11
Use preg_replace_callback instead like this:
$str = 'I220AB FRRRR CD I221ABCDEF I220AB DSFDSF CDEFG';
$repl= preg_replace_callback('~(I220[^\s]+)~', function($m) {
static $i=9;
return $m[1] . $i++;
}, $str);
echo $repl\n"; // I220AB9 FRRRR CD I221ABCDEF I220AB10 DSFDSF CDEFG
I dont know what your requirnments for adding the number at the end are so i just incremeneted during the loop;
$string = 'I220ABCD I220ABCDEF I220ABCDEFG';
$arrayStrings = explode(" ", $string);
$int = 9;
$newString = '';
foreach($arrayStrings as $stringItem)
{
if (preg_match("/I220.*/", $stringItem, $matches))
{
$stringItem = $stringItem.$int;
$newString = $newString.$stringItem." ";
$int++;
}
}
echo $newString;
Use preg_replace_callback():
$string = 'I220ABCD I220ABCDEF I220ABCDEFG';
// This requires PHP5.3+ since it's using an anonymous function
$result = preg_replace_callback('/I220[^\s]*/', function($match){
return($match[0].rand(0,10000)); // Add a random number between 0-10000
}, $string);
echo $result; // I220ABCD3863 I220ABCDEF5640 I220ABCDEFG989
Online demo.
You'll need to use a catch block in your regex e.g. "/I220([^ ]+)/" and if you want them all, you'll need to use preg_match_all, too.
preg_replace_callback with your needs:
$string = 'I220ABCD I220ABCDEF I220ABCDEFG';
class MyClass{
private static $i = 9;
private static function callback($matches){
return $matches[0] . self::$i++;
}
public static function replaceString($string){
return preg_replace_callback('/I220[^\s]+/',"self::callback",$string);
}
}
echo(MyClass::replaceString($string));
of course you can edit to class to initialize the way you want
I want to normalize (so canonicalize) a string into the normal form for names:
First letter of the name is uppercase
The difficulty by this is now to follow this rule with second and third name.
My method:
public function namilize($string)
{
$strings = explode(' ', $string);
foreach ($strings as $string) {
$string = ucfirst(strtolower($string));
}
$string = implode(' ', $strings);
return $string;
}
Somehow the
$string = ucfirst(strtolower($string));
fails.
What do I have to correct?
Is there a better way?
Regards
EDIT:
Hi,
thank you all for all the comments and answers.
I found another "modern" method:
public function namilize($string)
{
$string = mb_convert_case($string, MB_CASE_TITLE, mb_detect_encoding($string));
}
When I now would additionally add some regex for Mc and O's than it would be complete :)
public function namilize($name) {
$name = strtolower($name);
$normalized = array();
foreach (preg_split('/([^a-z])/', $name, NULL, PREG_SPLIT_DELIM_CAPTURE | PREG_SPLIT_NO_EMPTY) as $word) {
if (preg_match('/^(mc)(.*)$/', $word, $matches)) {
$word = $matches[1] . ucfirst($matches[2]);
}
$normalized[] = ucfirst($word);
}
return implode('', $normalized);
}
Note that this will work for names like John O'Brian, James McManus, etc. For other names with prefixes like McManus, simply add the prefix to the preg_match(). Obviously, this runs the possibility of false positives, but no method is going to be 100% foolproof.
You have to pass the $string by reference, note the &:
public function namilize($string)
{
$strings = explode(' ', $string);
foreach ($strings as &$string) {
$string = ucfirst(strtolower($string));
}
$string = implode(' ', $strings);
return $string;
}
Or use the function suggested by #thetaiko ucwords($string)
The $string inside the foreach will only store the last iteration (or the last name). This doesn't really matter though because the variable in the foreach is never used for output. The implode just undoes what you did with the explode so you will end up with the exact same output as the input. I changed the variable names to be more descriptive in this example:
function namilize($name_in)
{
$a_names = explode(' ', $name_in); //explode string into array
foreach ($a_names as $name) {
$a_fullname[] = ucfirst(strtolower($name)); //build array of proper case names
}
$string = implode(' ', $a_fullname); //convert array into string
return $string;
}
I've seen so many misuses of RegExp, I don't really like it :)
I have string (as a result of two str_replaces) that might look something like this:
.?This iš my ".stRiNg."!
|
V
--this-is-my---string---
Is there any way better than
$string = trim(preg_replace('/[-]+/u','-', $string),'-');
to get:
this-is-my-string
?
preg_replace() wins
<?php
function benchmark($callback){
echo sprintf('%-30s: ', $callback);
$t = microtime(true);
foreach(range(1, 10000) as $n){
call_user_func($callback);
}
echo (microtime(true)-$t)."\n";
}
function implode_explode_filter(){
implode('-', array_filter(explode('-', '--this-is-my---string---')));
}
function preg_replace_trim(){
preg_replace('/-+/', '-', trim('--this-is-my---string---', '-'));
}
function brant(){
$parts = explode("-",'--this-is-my---string---');
for($i=0;$i<count($parts);$i++) {
if (strlen($parts[$i]) < 1) {
unset($parts[$i]);
}
}
reset($parts);
$string = implode("-",$parts);
}
function murze_bisko(){
$string = "--this-is-my---string---";
while (strpos($string, "--") !== false) {
$string = str_replace("--", "-", $string);
}
$string = trim($string, '-'); # both of their answers were broken until I added this line
}
benchmark('implode_explode_filter');
benchmark('preg_replace_trim');
benchmark('brant');
benchmark('murze_bisko');
# Output
# implode_explode_filter : 0.062376976013184
# preg_replace_trim : 0.038193941116333
# brant : 0.11686086654663
# murze_bisko : 0.058025121688843
?>
I don't understand why you are looking for a 'better' way. Your way uses a simple regex in a place where it's perfectly appropriate to do so. What could be better than that?
print implode('-', array_filter( explode( '-', $string) ) );
Easy. :)
A better way? Probably not. Another way? Yes (essentially one-line version of Brant's answer):
implode('-', array_filter(explode('-', $string), function($s) { return strlen($s); }));
Note that you can't just use the naked array_filter reliably, because !!"0" == false in PHP.
$parts = explode("-",'--this-is-my---string---');
for($i=0;$i<count($parts);$i++) {
if (strlen($parts[$i]) < 1) {
unset($parts[$i]);
}
}
reset($parts);
$string = implode("-",$parts);
So you want to go from
--this-is-my---string---
to
this-is-my-string?
The best way would be a reg exp, but if you want a simple solution in php you can use
$string = "--this-is-my---string---";
while (! strpos($string, "--") === false) {
$string = str_replace("--", "-", $string);
}
After the loop $string will contain the result.
Just for the sake of the competition:
$string = str_replace('--','-', str_replace('--','-', '--this-is-my---string---'));
This is the fastest way to do it. It first replaces double -- with single and then cleans the rest again, so only single - remain.