• Вывод товаров по категориям учитывая вложенность, как сделать?

    Compolomus
    @Compolomus Куратор тега PHP
    Комполом-быдлокодер
    $config = array(
        'host' => 'localhost',
        'name' => 'test',
        'user' => 'root',
        'pass' => '',
    );
    
    $pdo = new \PDO('mysql:host=' . $config['host'] . ';dbname=' . $config['name'], $config['user'], $config['pass'],
        [
            \PDO::ATTR_ERRMODE => \PDO::ERRMODE_EXCEPTION,
            \PDO::ATTR_DEFAULT_FETCH_MODE => \PDO::FETCH_ASSOC,
            \PDO::MYSQL_ATTR_INIT_COMMAND => "SET NAMES 'utf8mb4'",
            \PDO::MYSQL_ATTR_USE_BUFFERED_QUERY,
        ]
    );
    
    $res = $pdo->query('select * from `products` order by `parent_id` asc');
    
    $cats = [];
    $structure = [];
    
    while ($row = $res->fetch()) {
        $cats[$row['id']] = $row;
        $structure[$row['parent_id']][] = $row['id'];
    }
    
    class Printer
    {
        private $cats = [];
        private $structure = [];
    
        public function __construct(array $cats, array $structure)
        {
            $this->setCats($cats);
            $this->setStructure($structure);
        }
    
        private function setCats(array $cats): void
        {
            $this->cats = $cats;
        }
    
        private function setStructure(array $structure): void
        {
            $this->structure = $structure;
        }
    
        protected function element(int $element): string
        {
            return '<a href="' . $this->cats[$element]['id'] . '">' . $this->cats[$element]['name'] . '</a>';
        }
    
        private function printElement(int $element, int $dept): string
        {
            $str = $this->element($element) . PHP_EOL;
            if (is_array($this->structure[$element]) && count($this->structure[$element]) > 0) {
                foreach ($this->structure[$element] as $id) {
                    $str .= $this->print($id, $dept + 1);
                }
            }
    
            return $str;
        }
    
        private function print(int $element, int $dept = 1): string
        {
            return '<ul><li>' . $this->printElement($element, $dept) . '</li></ul>' . PHP_EOL;
        }
    
        private function run(): string
        {
            return $this->print(current(current($this->structure)));
        }
    
        public function __toString(): string
        {
            return $this->run();
        }
    }
    
    echo(new Printer($cats, $structure));

    структура бд
    -- phpMyAdmin SQL Dump
    -- version 4.8.3
    -- https://www.phpmyadmin.net/
    --
    -- Хост: 127.0.0.1:3306
    -- Время создания: Фев 16 2019 г., 11:41
    -- Версия сервера: 8.0.12
    -- Версия PHP: 7.2.10
    
    SET SQL_MODE = "NO_AUTO_VALUE_ON_ZERO";
    SET AUTOCOMMIT = 0;
    START TRANSACTION;
    SET time_zone = "+00:00";
    
    
    /*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
    /*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
    /*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
    /*!40101 SET NAMES utf8mb4 */;
    
    --
    -- База данных: `test`
    --
    
    -- --------------------------------------------------------
    
    --
    -- Структура таблицы `products`
    --
    
    CREATE TABLE `products` (
      `id` int(11) NOT NULL,
      `name` varchar(255) COLLATE utf8mb4_general_ci NOT NULL,
      `parent_id` int(11) NOT NULL
    ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci;
    
    --
    -- Дамп данных таблицы `products`
    --
    
    INSERT INTO `products` (`id`, `name`, `parent_id`) VALUES
    (1, 'Рыбалка', 0),
    (2, 'Удилища', 1),
    (4, 'Спининговые', 2),
    (5, 'Морские', 2),
    (6, 'Катушки', 1);
    
    --
    -- Индексы сохранённых таблиц
    --
    
    --
    -- Индексы таблицы `products`
    --
    ALTER TABLE `products`
      ADD PRIMARY KEY (`id`);
    
    --
    -- AUTO_INCREMENT для сохранённых таблиц
    --
    
    --
    -- AUTO_INCREMENT для таблицы `products`
    --
    ALTER TABLE `products`
      MODIFY `id` int(11) NOT NULL AUTO_INCREMENT, AUTO_INCREMENT=7;
    COMMIT;
    
    /*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */;
    /*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */;
    /*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */;

    5c67cd0973e35415319613.png
    Ответ написан
    Комментировать
  • Как вы управляете своей базой знаний? Какие инструменты для этого используете?

    @yegreS
    Для хранения заметок я использую cherrytree (www.giuspen.com/cherrytree). Подкупила своей простотой, скоростью и возможностью ставить пароль на базу заметок
    Ответ написан
    Комментировать
  • Как называется карта прикосновений в системах анализа?

    @ComodoHacker
    Heatmap?
    Ответ написан
    Комментировать
  • Булевское свойство или функция

    EugeneOZ
    @EugeneOZ
    Заполненность поля сертификат говорит лишь о сертификате, о типе авторизации оно говорить не может. Может лишь косвенно намекать и этот намёк по стечению обстоятельств может быть правдивым — но полагаться на это 100% нельзя, особенно учитывая возможную эволюцию кода.
    Ответ написан
    Комментировать
  • Булевское свойство или функция

    С точки зрения эволюции кода, безопаснее использовать, например, перечисления (enum). Не «правильнее», а именно «безопаснее», в смысле будущих модификаций.

    Вдруг (наверняка?) у вас возникнет необходимость в дополнительных способах аутентификации (OAuth например)? В случае использования перечислений (или других аналогов шаблона «визитёр» — типа case classes из Scala), среда разработки подскажет вам, где вы забыли учесть новый вариант аутентификации. Не знаю как Visual Studio, а Eclipse или IDEA выдадут предупреждение в следующем коде:
    switch (principal.getAuthMethod()) {
    case LOGIN: /* Login / password auth */
        break;
    case CERTIFICATE: /* Certificate auth */
        break;
    }
    

    как только добавится новый тип аутентификации (OAUTH). Это даст вам знать, что вы забыли учесть новый способ ещё в каком-то месте.

    Так что если IDE помогает в таком деле, то почему бы этим не воспользоваться?
    Ответ написан
    Комментировать
  • Почему не запускается код на Java?

    @xaoc80
    Советую поставить NetBeans, тогда не будет головной боли по поводу запуска программ прямо из ID
    Ответ написан
    2 комментария
  • MySQL запрос из двух таблиц

    seriyPS
    @seriyPS
    Надеюсь эту картинку вы знаете?



    Допустим, таблица A это SELECT * FROM games, а таблица B это SELECT * FROM uploaded_games WHERE user_id = ?.

    Т.е. вам нужно из таблицы A вычесть таблицу B (в терминах теории множеств). На картинке это левый столбец, второй сверху.

    SELECT *
    FROM games as A
    LEFT JOIN uploaded_games as B ON (A.game_id = B.game_id)
    WHERE B.game_id is NULL AND B.user_id = ?
    


    Можно записать более наглядно, но, скорее всего, MySQL его не соптимизирует эффективно

    SELECT *
    FROM games
    WHERE game_id NOT IN (
      SELECT game_id FROM uploaded_games WHERE user_id = ?
    )
    
    Ответ написан
    Комментировать
  • Астрономический счет за интернет в роуминге, что делать?

    ks_ks
    @ks_ks
    Бежать из страны..)
    Ответ написан
    Комментировать
  • Как опубликовать пост на хабре?

    @BugMaker Автор вопроса
    Спасибо огромное! Вот, ради чего все затевалось
    Ответ написан
    Комментировать
  • Подкиньте идею мобильного приложения

    Shultc
    @Shultc
    RnD Developer
    Сделайте наконец сканер, который будет показывать, как выглядит человек без одежды. Все ждут. Все будут рады. ;)
    Ответ написан
    1 комментарий