'для' цикла по сравнению с 'foreach' QT в C++

ошибка означает, что ORM ожидает результирующий набор, включающий каждое свойство из FeedBacks, включая свойство с именем FeedbackUserName

. Поэтому вам нужно отредактировать предложение select вашего sql, чтобы оно возвращало все ожидаемые столбцы.

или вы можете использовать

Ms.Database.SqlQuery<SomeType>(
                   "your query here").ToList();

, где SomeType:

public class SomeType {
    public int Year {get; set;}        
    //... and/or all the pivoted columns
}
48
задан Adrian McCarthy 22 May 2013 в 06:24
поделиться

10 ответов

В большинстве случаев это действительно не имеет значения.

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

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

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

Сначала заставьте ваш код работать . Тогда заставьте его работать быстро (и только если вы обнаружите фактическую проблему с производительностью).

Время, потраченное на оптимизацию перед вами '

149
ответ дан 7 November 2019 в 12:01
поделиться

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

Но, конечно, ребята из Qt изучили его и фактически провели некоторое профилирование: http://blog.qt.io/blog/2009/01/23/iterating-efficiently/

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

23
ответ дан 7 November 2019 в 12:01
поделиться

Это действительно не имеет значения . Скорее всего, если ваша программа работает медленно, это не проблема. Однако следует отметить, что вы не проводите абсолютно равных сравнений. Qt foreach более похож на это (в этом примере будет использоваться QList ):

for(QList<QString>::iterator it = Con.begin(); it != Con.end(); ++it) {
    QString &str = *it;
    // your code here
}

Макрос может сделать это, используя некоторые расширения компилятора (например, GCC . ] __ typeof __ ), чтобы получить тип переданного контейнера. Также представьте, что Boost BOOST_FOREACH очень похож по своей концепции.

Причина, по которой ваш пример несправедлив, заключается в том, что ваша не-Qt-версия добавляет дополнительную работу.

Вы индексируете, а не действительно итерация. Если вы используете тип с несмежным распределением (я подозреваю, что это может быть в случае QList <> ), то индексирование будет более дорогим, так как код должен вычислять «где» n-й вещь есть.

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

РЕДАКТИРОВАТЬ: В качестве бонуса, в настоящее время я решительно поддерживаю версию итерации контейнера на C ++ 11, она чистая, лаконичная и простая:

for(QString &s : Con) {
    // you code here
}
14
ответ дан 7 November 2019 в 12:01
поделиться

Я не хочу отвечать на вопрос, который быстрее, но я хочу сказать, что лучше.

Самая большая проблема с foreach в Qt заключается в том, что он берет копию вашего контейнера, прежде чем перебирать его. Вы можете сказать «это не имеет значения, потому что классы Qt пересчитаны», но поскольку используется копия, вы фактически не меняете свой оригинальный контейнер.

Таким образом, foreach в Qt можно использовать только для циклов только для чтения, поэтому его следует избегать. Qt с радостью позволит вам написать цикл foreach, который, по вашему мнению, будет обновлять / модифицировать ваш контейнер, но в конце все изменения будут отброшены.

11
ответ дан 7 November 2019 в 12:01
поделиться

Во-первых, я полностью согласен с ответом, что «это не имеет значения». Выберите самое чистое решение и оптимизируйте его, если оно станет проблемой.

Но другой способ взглянуть на него состоит в том, что часто самым быстрым решением является то, которое наиболее точно описывает ваши намерения. В этом случае foreach QT говорит, что вы хотите применить какое-то действие к каждому элементу в контейнере.

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

Другими словами, цикл for упрощает проблему. Это добавляет много требований, которые на самом деле не являются частью того, что вы пытаетесь сделать. Ты не t заботиться о счетчике петель. Но как только вы пишете цикл for, он должен быть там.

С другой стороны, сотрудники QT не дали никаких дополнительных обещаний, которые могут повлиять на производительность. Они просто гарантируют итерацию по контейнеру и применение действия к каждому из них.

Другими словами, зачастую самое чистое и элегантное решение также является самым быстрым.

4
ответ дан 7 November 2019 в 12:01
поделиться

У foreach из Qt более четкий синтаксис для цикла for IMHO, так что в этом смысле он лучше. Мудрая производительность, я сомневаюсь, что есть что-то в этом.

Вы могли бы рассмотреть возможность использования BOOST_FOREACH вместо этого, так как это хорошо продуманный модный цикл, и он переносим (и, вероятно, когда-нибудь пробьется в C ++ и также пригоден для будущего).

3
ответ дан 7 November 2019 в 12:01
поделиться

Для небольших коллекций это должно иметь значение, и foreach имеет тенденцию быть более ясным.

Однако, для больших коллекций, в некоторый момент начнут биться foreach. (Предполагая, что оператор 'at ()' эффективен.

Если это действительно важно (и я предполагаю, что это так, как вы просите), тогда лучше всего измерить его. Профилировщик должен сделать трюк). Или вы можете создать тестовую версию с некоторыми инструментами.

2
ответ дан 7 November 2019 в 12:01
поделиться

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

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

Если у вас есть фактический массив, тогда от реализации языка и класса зависит, будет ли foreach быстрее для того же, что и для.

Если индексирование - это буквальное смещение памяти (такое как C ++), то for должно быть немного быстрее, поскольку вы избегаете вызов функции. Если индексирование является косвенным обращением, как и вызов, то оно должно быть таким же.

Все это, как говорится ... Мне трудно найти здесь причину для обобщения. Это последний вид оптимизации, который вам следует искать, даже если в вашем приложении есть проблемы с производительностью. Если у вас есть проблема с производительностью, которая может быть решена путем изменения способа итерации, у вас действительно нет проблем с производительностью. У вас есть БАГ, потому что кто-то написал либо очень дурацкий итератор, либо действительно дрянной индексатор.

тогда for должен быть немного быстрее, так как вы избегаете вызова функции. Если индексирование является косвенным обращением, как и вызов, то оно должно быть таким же.

Все это, как говорится ... Мне трудно найти здесь причину для обобщения. Это последний вид оптимизации, который вам следует искать, даже если в вашем приложении есть проблемы с производительностью. Если у вас есть проблема с производительностью, которая может быть решена путем изменения способа итерации, у вас действительно нет проблем с производительностью. У вас есть БАГ, потому что кто-то написал либо очень дурацкий итератор, либо действительно дрянной индексатор.

тогда for должен быть немного быстрее, так как вы избегаете вызова функции. Если индексирование является косвенным обращением, как и вызов, то оно должно быть таким же.

Все это, как говорится ... Мне трудно найти здесь причину для обобщения. Это последний вид оптимизации, который вам следует искать, даже если в вашем приложении есть проблемы с производительностью. Если у вас есть проблема с производительностью, которая может быть решена путем изменения способа итерации, у вас действительно нет проблем с производительностью. У вас есть БАГ, потому что кто-то написал либо очень дурацкий итератор, либо действительно дрянной индексатор.

Это последний вид оптимизации, который вам следует искать, даже если в вашем приложении есть проблемы с производительностью. Если у вас есть проблема с производительностью, которая может быть решена путем изменения способа итерации, у вас действительно нет проблем с производительностью. У вас есть БАГ, потому что кто-то написал либо очень дурацкий итератор, либо действительно дрянной индексатор.

Это последний вид оптимизации, который вам следует искать, даже если в вашем приложении есть проблемы с производительностью. Если у вас есть проблема с производительностью, которая может быть решена путем изменения способа итерации, у вас действительно нет проблем с производительностью. У вас есть БАГ, потому что кто-то написал либо очень дурацкий итератор, либо действительно дрянной индексатор.

0
ответ дан 7 November 2019 в 12:01
поделиться

Вы можете посмотреть на функцию STL for_each . Я не знаю, будет ли он быстрее двух представленных вами вариантов, но он более стандартизирован, чем foret в Qt, и позволяет избежать некоторых проблем, с которыми вы можете столкнуться при использовании обычного цикла for (а именно: индексация за пределами границ и трудности с переводом цикла в другую структуру данных).

0
ответ дан 7 November 2019 в 12:01
поделиться

Бенчмарк и его результаты можно найти на http://richelbilderbeek.nl/CppExerciseAddOneAnswer.htm

ИМХО (и многие другие здесь) это (то есть скорость) не имеет значения.

Но не стесняйтесь делать свои собственные выводы.

2
ответ дан 7 November 2019 в 12:01
поделиться
Другие вопросы по тегам:

Похожие вопросы: