Задать вопрос
Ответы пользователя по тегу PHP
  • Как разделить текст на 5 частей php?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    Если нужно получить параграфы примерно одинакового размера:
    $text = '...';
    
    $textSize = mb_strlen($text);
    $paragraphsCount = 5;
    $averageParagpaphSize = ceil($textSize / $paragraphsCount);
    
    $paragraphs = [];
    
    for ($i = 0; $i < $paragraphsCount; $i++)
    {
      $currentParagraph = mb_substr($text, $averageParagpaphSize * $i, $averageParagpaphSize);
      $paragraphs[] = $currentParagraph;
    }
    
    for ($i = 1; $i < $paragraphsCount; $i++)
    {
      $currentParagraph = $paragraphs[$i - 1];
      $nextParagraph = $paragraphs[$i];
    
      if (mb_substr($currentParagraph, -1, 1) !== '.')
      {
        $dotPosition = mb_strpos($nextParagraph, '.') + 1;
    
        $currentParagraph .= mb_substr($nextParagraph, 0, $dotPosition);
        $nextParagraph = trim(mb_substr($nextParagraph, $dotPosition));
      }
    
      $paragraphs[$i - 1] = $currentParagraph;
      $paragraphs[$i] = $nextParagraph;
    }
    
    var_dump($paragraphs);

    Тут не обработаны разные граничные случаи, но общий принцип ясен.
    Запустить

    Гораздо короче вариант, который предложил Михаил:
    $text = '...';
    $paragraphsCount = 5;
    
    $sentences = mb_split('\.', $text);
    $paragraphs = array_chunk($sentences, ceil(count($sentences) / $paragraphsCount));
    
    array_walk($paragraphs, function (&$paragraphSentences) {
      $paragraphSentences = implode(' ', $paragraphSentences);
    });
    
    var_dump($paragraphs);

    Запустить
    Правда, здесь в параграфах получается одинаковое количество предложений, но по длине они отличаются сильнее.
    Ответ написан
    Комментировать
  • Какой раздел PHP изучить для реализации указанно функционала?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    Php ничего не знает о слайдерах, новостях и картинках. Это язык широкого профиля, поэтому и разделы в нем абстрактные, базовые.
    Поэтому, вам сначала нужно понять как вы будете реализовывать этот функционал, на псевдокоде. Если где-то в вашем псевдокоде будет шаг "Добавляем строку в БД" - изучайте БД; при наличии шага "Сохраняем загруженный файл на сервер" - работу с файлами и формами и т.д.
    Ответ написан
    Комментировать
  • Как проверить, входит ли текущее время в заданный диапазон?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    Алгоритм тут достаточно простой - вам нужно диапазон преобразовать в две даты - начало и конец диапазона.
    А потом просто сравнить текущее время с ними.
    Разбивка диапазона - операция достаточно простая, попробуйте справиться самостоятельно и если что-то не получится, приходите снова с конкретными вопросами.

    Накидал примерное решение из интереса. Рекомендую всё-таки решить задачу самостоятельно и потом сравнить.
    Spoiler alert!
    $periodString = '12:00-02:00';
    $weekDay = 'Friday';
    
    $period = [
    	'start' => new DateTime(),
    	'end' => new DateTime(),
    ];
    
    $day = (int)date('d', strtotime('this '.$weekDay));
    $month = (int)date('m', strtotime('this '.$weekDay));
    $year = (int)date('Y', strtotime('this '.$weekDay));
    
    foreach (array_combine(['start', 'end'], explode('-', $periodString)) as $type => $part)
    {
    	list($hour, $minute) = explode(':', $part);
    	$hour = (int)$hour;
    	$minute = (int)$minute;
    
    	$date = $period[$type];
    
    	$date->setDate($year, $month, $day);
    	$date->setTime($hour, $minute);
    }
    
    if ($period['start'] > $period['end'])
    {
    	$period['end']->add(new DateInterval('P1D'));
    }
    
    $now = new DateTime();
    
    $isInInterval = $now >= $period['start'] && $now <= $period['end'];
    
    var_dump($isInInterval);



    А можно пойти немного дальше:
    Бугага :)
    class Interval
    {
    	private $data;
    	private $timezone;
    	private $start;
    	private $end;
    
    	public function __construct($serialized, $timezoneName = 'UTC')
    	{
    		$this->parse($serialized);
    		$this->timezone = new DateTimeZone($timezoneName);
    		$this->makeStart();
    		$this->makeEnd();
    	}
    
    	public function contains(DateTimeInterface $date)
    	{
    		return $date >= $this->start && $date <= $this->end;
    	}
    
    	public function isNow()
    	{
    		$now = new DateTimeImmutable('now', $this->timezone);
    		return $this->contains($now);
    	}
    
    	private function parse($serialized)
    	{
    		$parts = explode('-', $serialized);
    
    		$this->data = [
    			'start' => $this->parsePart($parts[0]),
    			'end' => $this->parsePart($parts[1]),
    		];
    	}
    
    	private function makeStart()
    	{
    		$this->start = $this->makeDate($this->data['start']['hour'], $this->data['start']['minute']);
    	}
    
    	private function makeEnd()
    	{
    		$this->end = $this->makeDate($this->data['end']['hour'], $this->data['end']['minute']);
    		$this->ensureEndIsAfterStart();
    	}
    
    	private function parsePart($part)
    	{
    		list($hour, $minute) = explode(':', $part);
    
    		return [
    			'hour' => $hour,
    			'minute' => $minute,
    		];
    	}
    
    	private function makeDate($hour, $minute)
    	{
    		list($day, $month, $year) = explode('.', date('d.m.Y'));
    
    		$date = new DateTime('now', $this->timezone);
    
    		$date->setDate($year, $month, $day);
    		$date->setTime($hour, $minute);
    
    		return $date;
    	}
    
    	private function ensureEndIsAfterStart()
    	{
    		if ($this->start > $this->end)
    		{
    			$this->end->add(new DateInterval('P1D'));
    		}
    	}
    }
    
    
    
    // Примеры использования:
    $interval = new Interval('11:59-02:00', 'Europe/Moscow');
    var_dump($interval->isNow());
    
    $date = new DateTime('now', new DateTimeZone('Europe/Moscow'));
    $date->add(new DateInterval('PT8H'));
    var_dump($interval->contains($date));

    Ответ написан
    23 комментария
  • Как быстро вшить полупрозрачный текст в изображение на php?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    Ну так вы кешируйте картинки с водяными знаками и создавайте их при добавлении изображений, а не при выводе. Контент-редактор две секунды может и потерпеть.
    Ответ написан
  • Как записать название текущего файла в переменную?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    foreach ($_FILES["files"]["error"] as $key => $error) {
        if ($error == UPLOAD_ERR_OK) {
            $tmp_name = $_FILES["files"]["tmp_name"][$key];
            ${'file_'.$key} = $_FILES["files"]["name"][$key];
            move_uploaded_file($tmp_name, "uploads/$name");
            
        }
    }

    Ну а вообще, конечно, правильнее писать в массив, а не плодить кучу переменных через костыли.
    Ответ написан
    Комментировать
  • Как спрятать блок, если нету данных?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    <?php
    $custom_field_name = [];
    
    if (osc_count_item_meta() >= 1)
    {
    	while (osc_has_item_meta())
    	{
    		if (osc_item_meta_value() != "")
    		{
    			$custom_field_name [osc_item_meta_slug()] = osc_item_meta_name();
    			$custom_field_value [osc_item_meta_slug()] = osc_item_meta_value();
    		}
    	}
    }
    
    if (
    	array_key_exists('additional_file', $custom_field_name) && array_key_exists('additional_file', $custom_field_value) &&
    	array_key_exists('put_kesh', $custom_field_name) && array_key_exists('put_kesh', $custom_field_value)
    ): ?>
    <div class="block_list">
    	<div id="useful_info">
    		<h2 class="title">
    			<?php _e('Дополнительные файлы', OSCLASSWIZARDS_THEME_FOLDER); ?>
    		</h2>
    		<p class="left"><?= $custom_field_name ['additional_file']; ?> : <strong> <?= $custom_field_value ['additional_file']; ?></strong></p>
    		<p class="left"><?= $custom_field_name ['put_kesh']; ?> : <strong> <?= $custom_field_value ['put_kesh']; ?></strong></p>
    	</div>
    </div>
    <?php endif ?>
    Ответ написан
    3 комментария
  • Почему Битрикс комментирует код вывода характеристики, вызываемый через echo?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    <?= - это и есть echo. Зачем вы пытаетесь вывести его второй раз в виде строки?
    switch ($strPath)
    {
    case '/catalog/kategioria1/index.php':
         echo $arElement["SIZE"];
         break;
    case '/catalog/kategioria2/index.php':
         echo $arElement["WIEGHT"];
         break;
    default:
         echo $arElement["BRAND"];
         break;
    }
    Ответ написан
    Комментировать
  • Как из массива вывести только 3 первых элемента?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    <?php foreach (array_slice($category['children'], 0, 3) as $child) { ?>
    <li><a href="<?php echo $child['href']; ?>"><?php echo $child['name']; ?></a></li>
    <?php } ?>
    Ответ написан
    Комментировать
  • Почему не приходит письмо полностью, а только часть?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    $messages = "Фамилия: {$familija}\n";
    $messages = "ИНН: {$inn}\n";
    В этих местах вы переопределяете значение переменной $messages. Все, что было записано в нее до этого, удаляется. Чтобы этого избежать, нужно присвоение = заменить конкатенацией .=.
    Ответ написан
    Комментировать
  • Как можно выделить наименьшее по длине предложение из строки?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    Вообще, регулярные выражения не подходят для парсинга естественного языка.
    Например, совершенно валидный с точки зрения языка текст
    Иван, недавно переехавший в город N. спросил: «Как твои дела?» - и протянул однокласснице букет полевых цветов. Она смутилась и покраснела, но букет приняла. Смеркалось...
    вы не разберете на предложения никакой регуляркой (и это я еще из Толстого пример не взял).
    Поэтому вам сначала нужно составить формальный набор правил и ограничений, которому должен подчиняться ваш текст и только тогда мы сможем вам помочь составить под этот набор регулярное выражение.
    Ответ написан
    5 комментариев
  • Для чего и главное где используются {} в php?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    $release->{"country-code"} или $release->{"@country"}

    country-code и @country - это свойства объекта, но написать $release->country-code или $release->@country нельзя, это не переварится интерпретатором. Поэтому и используется такой способ.
    Подробнее можно прочитать, разумеется, в документации.

    return "{$this->product}"
    А вот это - дурацкий хак. Насколько я понимаю, это сделано для того, чтобы возвращать строковое представление объекта product. Но гораздо нагляднее делать $this->product->__toString().
    Вот пример такой системы:
    class Product {
    	public function __toString() {
    		return 'foo';
    	}
    }
    
    class Thing {
    	private $product;
    	
    	public function __construct() {
    		$this->product = new Product;
    	}
    	
    	public function bar() {
    		// Писать меньше и можно гордиться своим крутым маневром
    		// Но через месяц надо вспоминать, зачем это кавычки вокруг свойства
    		return "$this->product";
    
    		// Наглядно и понятно, никакой магии
    		return $this->product->__toString();
    	}
    }
    
    $thing = new Thing();
    var_dump($thing->bar());
    Ответ написан
    4 комментария
  • Зачем использовать isset&&!empty для инпута?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    Если в текстовом поле, например, ничего не ввели, то и на сервер это поле не передастся.
    Если делать проверку только по empty($_POST['foo']), то вылезет NOTICE - Undefined index: foo.
    Хороший программист делает так, чтобы код не кидал никаких уведомлений, чтобы спустия несколько месяцев не ловить в продакшене рандомные баги.
    Можно проверять через array_key_exists('foo', $_POST), но это значительно дольше набирать.
    Ответ написан
    5 комментариев
  • Как с помощью php делать копию сайта?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    Давайте рассуждать:
    • Сайт состоит из набора файлов и, возможно, БД
    • Значит, копирование сайта заключается в:
      1. копировании файлов
      2. копировании БД
      3. настройке веб-сервера



    С каким из этапов у вас сложности?
    Ответ написан
    8 комментариев
  • Почему PDO query не хочет выводить контент?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    скрипт выводит только строку title в таблице news

    SELECT title FROM news

    "Действительно, в чем же причина такого странного поведения?" - спросил Алексей Уколов с явным сарказмом в голосе.
    Ответ написан
    2 комментария
  • Автоматический счетчик? Разметка в цикле?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    Алгоритм, на самом деле, довольно прост:
    <div class="container">
    <div class="row">
    <?php
    for($i = 0; $i < 10; $i++)
    {
    	echo '<div class="col-md-4 col-xs-12">Запись '.$i.'</div>';
    	
    	if ($i % 3 == 2)
    	{
    		echo '</div>';
    		echo '<div class="row">';
    	}
    }
    ?>
    </div>
    </div>

    У него есть один недостаток - в конце может получиться пустой .row, но этого можно избежать, добавив проверку на последнюю итерацию:
    $ar = range(0, 11);
    $size = count($ar) - 1;
    
    foreach($ar as $i => $v)
    {
    	echo '<div class="col-md-4 col-xs-12">Запись '.$v.'</div>';
    	
    	if ($v % 3 == 2 && $i < $size)
    	{
    		echo '</div>';
    		echo '<div class="row">';	
    	}
    }
    Ответ написан
    Комментировать
  • Регулярные выражения?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    $string = '!rand 1-10'; // или $_POST['text'], как в вашем случае
    
    $matches = [];
    
    if (preg_match_all('/!rand (\d+)-(\d+)/', $string, $matches))
    {
        $min = (int)$matches[1][0];
        $max = (int)$matches[2][0];
    
        echo rand($min, $max);
    }
    Ответ написан
    Комментировать
  • Почему так происходит?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    Потому что в первом случае вы в $new_events присваиваете результат сравнения $order->get_new_events_count('comments') > 0 (это может быть true или false).

    echo true;  // выведет "1"
    echo false; // выведет "" (пустую строку).

    Поэтому, какое бы число ни возвращала функция get_new_events_count, если оно больше 0 - всегда будет выводиться цифра 1.

    Правильно делать так:
    <?php
    $new_events = $order->get_new_events_count('comments');
    ?>
    <?php if ($new_events > 0): ?>
        <?= $new_events; ?>
    <?php endif; ?>


    Можно было бы написать то же самое вот так:
    <? if (($new_events = $order->get_new_events_count('comments')) > 0): ?>
        <?= $new_events; ?>
    <? endif; ?>

    Но, сами видите, в таком коде легко допустить ошибку. Присвоение внутри оператора сравнения считается плохой практикой, помимо проблем с порядком выполнения нередки ситуации, когда разработчик пишет if ($foo = $bar), вместо if ($foo == $bar)

    А во втором в if выполняется нормальная проверка, но функция get_new_events_count вызывается дважды, вы, судя по всему, именно этого хотите избежать.
    Ответ написан
    Комментировать
  • На сколько правильно использовать для composer-а git форки (fork) в своём проекте?

    alexey-m-ukolov
    @alexey-m-ukolov Куратор тега PHP
    Если у вас такая дикая паранойя - пишите свои велосипеды.
    Форки вас не спасут. Форкать и потом все-равно сливать обновления из базового репозитория - бессмысленный труд, все-равно нужно код тщательно просматривать, анализировать все изменения. Ну так это и без форка можно сделать - перед установкой новой версии просто смотрите все коммиты.
    Ответ написан
    Комментировать