Получить первые 100 символов из строки, соблюдая полные слова


Я уже задавал подобный вопрос здесь раньше, но мне нужно знать, возможна ли эта небольшая настройка. Я хочу сократить строку до 100 символов и использовать $small = substr($big, 0, 100); чтобы сделать так. Однако, это только первые 100 символов и неважно, нарушает ли он слово или нет.

есть ли способ взять до первых 100 символов строки, но убедитесь, что вы не нарушаете слово?

пример:

$big = "This is a sentence that has more than 100 characters in it, and I want to return a string of only full words that is no more than 100 characters!"

$small = some_function($big);

echo $small;

// OUTPUT: "This is a sentence that has more than 100 characters in it, and I want to return a string of only"

есть ли способ сделать это с помощью PHP?

18 60

18 ответов:

все, что вам нужно сделать, это использовать:

$pos=strpos($content, ' ', 200);
substr($content,0,$pos ); 

Да, есть. Это функция, которую я заимствовал у пользователя на разных форумах несколько лет назад, поэтому я не могу взять на себя ответственность за нее.

//truncate a string only at a whitespace (by nogdog)
function truncate($text, $length) {
   $length = abs((int)$length);
   if(strlen($text) > $length) {
      $text = preg_replace("/^(.{1,$length})(\s.*|$)/s", '\1...', $text);
   }
   return($text);
}

обратите внимание, что он автоматически добавляет троеточие, если вы не хотите, чтобы просто использовать '\1' в качестве второго параметра для preg_replace звонок.

Если вы определяете слова как"последовательности символов, разделенных пробелом"... Используйте strrpos() чтобы найти последний пробел в строке, сократите до этой позиции, обрезать результат.

конечно. Самый простой, вероятно, написать обертку вокруг preg_match:

function limitString($string, $limit = 100) {
    // Return early if the string is already shorter than the limit
    if(strlen($string) < $limit) {return $string;}

    $regex = "/(.{1,$limit})\b/";
    preg_match($regex, $string, $matches);
    return $matches[1];
}

EDIT: обновлено, чтобы не всегда включать пробел в качестве последнего символа в строке

эта функция сокращает строку, добавляя "..." на границе слова, когда это возможно. Возвращаемая строка будет иметь максимальную длину $len в том числе "...".

function truncate($str, $len) {
  $tail = max(0, $len-10);
  $trunk = substr($str, 0, $tail);
  $trunk .= strrev(preg_replace('~^..+?[\s,:]\b|^...~', '...', strrev(substr($str, $tail, $len-$tail))));
  return $trunk;
}

примеры выходов:

  • truncate("Thanks for contributing an answer to Stack Overflow!", 15)
    возвращает "Thanks for..."
  • truncate("To learn more, see our tips on writing great answers.", 15)
    возвращает "To learn more..." (запятая и усе)
  • truncate("Pseudopseudohypoparathyroidism", 15)
    возвращает "Pseudopseudo..."

Это мой подход, основанный на ответе Амира, но он не позволяет ни одному слову сделать строку длиннее предела, используя strrpos() с отрицательным смещением.

простой, но работает. Я использую тот же синтаксис, что и в вспомогательной функции Str_limit() Laravel, если вы хотите использовать ее в проекте, отличном от Laravel.

function str_limit($value, $limit = 100, $end = '...')
{
    $limit = $limit - mb_strlen($end); // Take into account $end string into the limit
    $valuelen = mb_strlen($value);
    return $limit < $valuelen ? mb_substr($value, 0, mb_strrpos($value, ' ', $limit - $valuelen)) . $end : $value;
}

Это прекрасно работает для меня, я использую его в мой скрипт

<?PHP
$big = "This is a sentence that has more than 100 characters in it, and I want to return a string of only full words that is no more than 100 characters!";
$small = some_function($big);
echo $small;

function some_function($string){
     $string = substr($string,0,100);
     $string = substr($string,0,strrpos($string," "));
     return $string;
}
?>

удачи

вот отличное решение с точками в конце с полными словами

function text_cut($text, $length = 200, $dots = true) {
    $text = trim(preg_replace('#[\s\n\r\t]{2,}#', ' ', $text));
    $text_temp = $text;
    while (substr($text, $length, 1) != " ") { $length++; if ($length > strlen($text)) { break; } }
    $text = substr($text, 0, $length);
    return $text . ( ( $dots == true && $text != '' && strlen($text_temp) > $length ) ? '...' : ''); 
}

вход: Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ут еним объявление veniam миним, магазина nostrud exercitation ullamco laboris на Ниси ут aliquip ex для компании ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. За исключением Синт occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.

выход: Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip...

Это сделало это для меня...

//trim message to 100 characters, regardless of where it cuts off
$msgTrimmed = mb_substr($var,0,100);

//find the index of the last space in the trimmed message
$lastSpace = strrpos($msgTrimmed, ' ', 0);

//now trim the message at the last space so we don't cut it off in the middle of a word
echo mb_substr($msgTrimmed,0,$lastSpace)

вот мое решение:

/**
 * get_words_until() Returns a string of delimited text parts up to a certain length
 * If the "words" are too long to limit, it just slices em up to the limit with an ellipsis "..."
 *
 * @param $paragraph - The text you want to Parse
 * @param $limit - The maximum character length, e.g. 160 chars for SMS
 * @param string $delimiter - Use ' ' for words and '. ' for sentences (abbreviation bug) :)
 * @param null $ellipsis - Use '...' or ' (more)' - Still respects character limit
 *
 * @return string
 */
function get_words_until($paragraph, $limit, $delimiter = ' ', $ellipsis = null)
{
    $parts = explode($delimiter, $paragraph);

    $preview = "";

    if ($ellipsis) {
        $limit = $limit - strlen($ellipsis);
    }

    foreach ($parts as $part) {
        $to_add = $part . $delimiter;
        if (strlen($preview . trim($to_add)) <= $limit) { // Can the part fit?
            $preview .= $to_add;
            continue;
        }
        if (!strlen($preview)) { // Is preview blank?
            $preview = substr($part, 0, $limit - 3) . '...'; // Forced ellipsis
            break;
        }
    }

    return trim($preview) . $ellipsis;
}

в вашем случае это будет (например):

$big = "This is a sentence that has more than 100 characters in it, and I want to return a string of only full words that is no more than 100 characters!"

$small = get_words_until($big, 100);
function truncate ($str, $length) {
    if (strlen($str) > $length) {
        $str = substr($str, 0, $length+1);
        $pos = strrpos($str, ' ');
        $str = substr($str, 0, ($pos > 0)? $pos : $length);
    }
    return $str;
}

пример:

print truncate('The first step to eternal life is you have to die.', 25);

строка(25) "первый шаг к вечной"

print truncate('The first step to eternal life is you have to die.', 12);

строка(9) "первый"

print truncate('FirstStepToEternalLife', 5);

строка(5) "Первый"

Я прошу прощения за воскрешение этого вопроса, но я наткнулся на эту тему и нашел небольшую проблему. Для тех, кто хочет ограничить символ, который удалит слова, которые будут идти выше вашего данного предела, приведенные выше ответы отлично работают. В моем конкретном случае мне нравится отображать слово, если предел падает в середине указанного слова. Я решил поделиться своим решением, если кто - то еще ищет эту функциональность и должен включать слова вместо их обрезки из.

function str_limit($str, $len = 100, $end = '...')
{
    if(strlen($str) < $len)
    {
        return $str;
    }

    $str = preg_replace("/\s+/", ' ', str_replace(array("\r\n", "\r", "\n"), ' ', $str));

    if(strlen($str) <= $len)
    {
        return $str;
    }

    $out = '';
    foreach(explode(' ', trim($str)) as $val)
    {
        $out .= $val . ' ';

        if(strlen($out) >= $len)
        {
            $out = trim($out);
            return (strlen($out) == strlen($str)) ? $out : $out . $end;
        }
    }
}

примеры:

  • вход: echo str_limit('Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.', 100, '...');
  • выход: Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore...
  • вход: echo str_limit('Lorem ipsum', 100, '...');
  • выход: Lorem ipsum
  • вход: echo str_limit('Lorem ipsum', 1, '...');
  • выход: Lorem...

вот еще один способ вы можете сделать это.

$big = "This is a sentence that has more than 100 characters in it, and I want to return a string of only full words that is no more than 100 characters!"
$big = trim( $big );
$small = $big;
                if( strlen( $big ) > 100 ){
                $small = mb_substr( $small, 0, 100 );
                $last_position = mb_strripos( $small, ' ' );
                    if( $last_position > 0 ){
                    $small = mb_substr( $small, 0, $last_position );
                    }
                }

            echo $small; 

или

 echo ( strlen( $small ) <  strlen( $big ) ? $small.'...' : $small );

Это также многобайтовый сейф, а также работает, даже если нет пробелов, и в этом случае он просто вернет первые 100 символов. Он принимает первые 100 символов, а затем выполняет поиск от конца до ближайшего разделителя слов.

проблема с принятой ответ, что результат выходит за предел, т. е. она может превышать 100 символов, начиная с strpos будет выглядеть после смещение и поэтому ваша длина всегда будет превышать ваш предел. Если последнее слово длинное, как squirreled тогда длина вашего результата будет 111 (чтобы дать вам представление).

лучшее решение-использовать :

function truncate($str, $length = 125, $append = '...') {
    if (strlen($str) > $length) {
        $delim = "~\n~";
        $str = substr($str, 0, strpos(wordwrap($str, $length, $delim), $delim)) . $append;
    } 

    return $str;
}


echo truncate("The quick brown fox jumped over the lazy dog.", 5);

таким образом, вы можете быть уверены, что строка обрезается под ваш предел (и никогда не переходит)

П. С. это особенно полезно, если вы планируете хранить усеченную строку в своей базе данных с фиксированным столбцом, таким как VARCHAR(50) и т. д.

П. П. С. обратите внимание на специальный разделитель в wordwrap. Это необходимо для того, чтобы убедиться, что ваша строка усекается правильно, даже если она содержит новые строки (в противном случае она будет усекать сначала новую строку, которую вы не хотите).

другой более простой способ я делаю.

function limit_words($string, $word_limit = 10)
{
    $words = explode(" ", $string);
    if (count($words) > $word_limit) {
        return implode(" ", array_splice($words, 0, $word_limit)) . ' ...';
    }
    return implode(" ", array_splice($words, 0, $word_limit));
}

wordwrap форматирует строку в соответствии с limit, разделяет их с \n таким образом, у нас есть линии меньше 50, Орды не разделены взрывает строку seprates согласно \n Итак, у нас есть массив, соответствующий строкам список собирает первый элемент.

list ($short) = explode ("\n", wordwrap($ali, 50));

пожалуйста, рэп Эверт, так как я не могу комментировать или rep.

вот пример запуска

php >  $ali = "ali veli krbin yz doksan esikesiksld sjkas laksjald lksjd asldkjadlkajsdlakjlksjdlkaj aslkdj alkdjs akdljsalkdj ";
php > list($short) = explode("\n",wordwrap($ali ,50));
php > var_dump($short);
string(42) "ali veli krbin yz doksan esikesiksld sjkas"
php > $ali ='';
php > list($short) = explode("\n",wordwrap($ali ,50));
php > var_dump($short);
string(0) ""

еще один ответ! Я не был полностью удовлетворен другими ответами и хотел "жесткого отсечения" (гарантированный разрыв слов перед $max_characters, если это возможно), так что вот моя функция, чтобы внести свой вклад!

/**
 * Shortens a string (if necessary), trying for a non-word character before character limit, adds an ellipsis and
 * returns. Falls back to a forced cut if no non-word characters exist before.
 *
 * @param string $content
 * @param int    $max_characters - number of characters to start looking for a space / break.
 * @param bool   $add_ellipsis   - add ellipsis if content is shortened
 *
 * @return string
 */
public static function shorten( $content, $max_characters = 100, $add_ellipsis = TRUE ) {
    if ( strlen( $content ) <= $max_characters ) {
        return $content;
    }

    // search for non-word characters
    $match_count = preg_match_all( '/\W/', $content, $matches, PREG_OFFSET_CAPTURE );

    // force a hard break if can't find another good solution
    $pos = $max_characters;

    if ( $match_count > 0 ) {
        foreach ( $matches[0] as $match ) {
            // check if new position fits within
            if ( $match[1] <= $max_characters ) {
                $pos = $match[1];
            } else {
                break;
            }
        }
    }

    $suffix = ( $add_ellipsis ) ? '&hellip;' : '';

    return substr( $content, 0, $pos ) . $suffix;
}

## получить первый ограниченный символ из строки ##

<?php 
  $content= $row->title;
  $result = substr($content, 0, 70);
  echo $result; 
  ?>