LINUX.ORG.RU

Два стула: процессорное время или потребление памяти?

 ,


1

1

Назрел ещё один насущный вопрос. Не знаю как у других реализаций SQL, но при использовании SQLite3 в качестве БД для сайта на PHP, мы имеем весьма скудное API, которое не позоволяет перемещаться по результатам выборки из базы, выдёргивать любые данные из любого места, да даже нельзя узнать количество строк (rows) в результате $try = $dbh->query(); выполнения запроса SQLite3! Только если выполнить отдельный COUNT(*), но это уже будет второй запрос.

Всё, что можно, это лишь вывести результат запроса. <?php while ($row = $try->fetchArray()): extract($row); unset($row); ?><?php endwhile; ?>.

Возвращаясь к выбору между нагрузкой на процессор и потребляемой php-скриптом памятью.

Самое простое, нам нужно узнать сколько «строк» (rows) мы имеем в результате выборки из базы.

Вариант 1) сделать $lines++; в цикле при выводе (но тогда нельзя будет сразу сделать постраничную навигацию, потому что количество строк требуется знать заранее).

Вариант 2) предварительно сохранить весь результат выборки в массив, таким образом php-скрипт отожрёт приличное количество памяти.

Едем дальше. Нам нужно вывести данные с учётом других таблиц, допустим вывести все статьи и комментарии к каждой статье, и здесь дилемма: как лучше, сделать один раз JOIN чтобы подключить комментарии к статьям, либо сделать цикл внутри цикла: один SELECT, чтобы вывести все статьи, а потом ещё в каждой статье делать SELECT чтобы отдельно вывести все комментарии к статье?

Много SELECT'ов мне кажется ламерским способом выводить данные на сайт. И тогда мы возвращаемся к нашему JOIN таблиц статей и комментариев.

Как вы знаете, результатом JOIN будет повторение данных в некоторых случаях:

статья 1 | комментарий 1
статья 2 | комментарий 1
статья 2 | комментарий 2

но выводим-то мы всё в одном цикле, и чтобы не получилось так, что «статья 2» вывелась два раза из-за двух комментариев к ней, то придётся в цикле расставлять проверки, дескать «статья уже была выведена, значит выведи только комментарий к ней».

Что лучше, предварительно считать всё в массив на php, и это отожрёт много памяти на один запрос, либо, выполнять SELECT с JOIN'ами в цикле, но уже в самом цикле выполнять проверки которые излишне нагрузят процессор?

Кратко: много SELECT'ов внутри многих циклов ИЛИ один SELECT с JOIN'ами и одним циклом для вывода всего?

★★★★★

Последнее исправление: Spoofing (всего исправлений: 1)

Что же вы за сайт пишете, что вывод комментариев любым из этих способов стал узким местом? Мегапортал с огромной посещаемостью? Или из любви к искусству?

Кратко: много SELECT'ов внутри многих циклов ИЛИ один SELECT с JOIN'ами и одним циклом для вывода всего?

Если кратко, то из этих двух вариантов лучше второй. Каждый SELECT - это установка соединения с БД и его разрыв по завершению = накладные расходы. Кроме того, в плане скорости фильтраций и выборок SQL намного быстрее PHP, поскольку заточена на это. Не знаю, относится ли это к SQLite, но к MySQL/Maria/PG относится точно.

tired_eyes
()
Ответ на: комментарий от tired_eyes

Или из любви к искусству?

хорошо, спасибо за совет, буду заниматься фильтрацией на стороне sql.

Spoofing ★★★★★
() автор топика
Ответ на: комментарий от tired_eyes

Каждый SELECT - это установка соединения с БД и его разрыв по завершению = накладные расходы.

Что пул соединений для народа не доступен?

Deleted
()
Ответ на: комментарий от tired_eyes

не будет ли для уважаемого дона откровением что это можно написать руками, и даже есть готовые библиотеки для пула соединений, в некоторых яп даже несколько.

Deleted
()
Ответ на: комментарий от Deleted

это можно написать руками

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

tired_eyes
()
Ответ на: комментарий от Deleted

готового наверное нет ничего такого

anonymous
()
Ответ на: комментарий от tired_eyes

в принципе React есть, но это усложнение

anonymous
()
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.