мне нужно вычислить временную сложность следующего кода:Временная сложность вложенная для цикла
for (i = 1; i <= n; i++)
{
for(j = 1; j <= i; j++)
{
// Some code
}
}
ли это O (N^2)?
мне нужно вычислить временную сложность следующего кода:Временная сложность вложенная для цикла
for (i = 1; i <= n; i++)
{
for(j = 1; j <= i; j++)
{
// Some code
}
}
ли это O (N^2)?
Действительно, это O (n^2). См. Также очень похожий пример с тем же временем выполнения here.
Да, вложенные петли - это один из способов быстро получить большую нотацию O.
Обычно (но не всегда) одна петля, вложенная в другую, вызывает O (n²).
Подумайте об этом, внутренний цикл выполняется i раз, для каждого значения i. Внешний цикл выполняется n раз.
, таким образом, вы видите картину исполнения, как это: 1 + 2 + 3 + 4 + ... + п раз
Поэтому мы можем оценить число кодовых казней, говоря, что, очевидно, выполняет более n раз (нижняя граница), но в терминах n сколько раз мы выполняем код?
Ну, математически мы можем сказать, что он выполнит не более n² раз, что даст нам худший сценарий и, следовательно, нашу грань O-O (n²). (Для получения дополнительной информации о том, как мы можем математически сказать этот взгляд на Power Series)
Big-Oh не всегда точно определяет, сколько работы выполняется, но обычно дает надежную аппроксимацию наихудшего сценария.
4г позже Edit: Поскольку этот пост, кажется, чтобы получить достаточное количество трафика. Я хочу более подробно объяснить, как мы связали выполнение с O (n^2) с использованием степенных рядов
От веб-сайта: 1 + 2 + 3 + 4 ... + n = (n² + n)/2 = n²/2 + n/2. Как же мы превращаем это в O (n²)? Мы в основном говорим, что n²> = n²/2 + n/2. Это правда? Давайте сделаем простую алгебру.
Должно быть ясно, что n²> = n (не строго больше, из-за случая, когда n = 0 или 1), считая, что n всегда является целым числом.
Актуальная сложность Big O немного отличается от того, что я только что сказал, но это ее суть. На самом деле, сложность Big O задает, есть ли константа, которую мы можем применить к одной функции, такой, что она больше другой, для достаточно большого ввода (см. Страницу wikipedia)
Могу я задать здесь небольшой вопрос? что, если часть «// some code» является некоторым вычислением с сложностью O (N), как вычисляется результат? Я думаю, что это обычный случай, когда одна функция вызывает другую и рассматривает позже как черный ящик, имеющий некоторую сложность, предоставляемую спецификациями? –
@ShawnLe: Проницательное наблюдение. В большинстве предположений да, мы предполагаем, что '// некоторый код' равен O (1) и, следовательно, не учитывается в сложности Big O. Если бы это было на самом деле O (N), то наша общая сложность стала O (N^3). Подумайте об этом как о умножении (потому что это так). Для итераций внешнего цикла ~ N внутренний цикл повторяется ~ N раз, причем каждая итерация выполняет работу ~ N. N раз N раз N = N^3. – AndyG
Сначала мы рассмотрим петли, где число итерации внутреннего цикла не зависят от значения индекса внешнего цикла.Например:
for (i = 0; i < N; i++) {
for (j = 0; j < M; j++) {
sequence of statements
}
}
Внешний цикл выполняет N раз. Каждый раз, когда выполняется внешний цикл, внутренний цикл выполняет M раз. В результате, операторы во внутреннем цикле выполняют в общей сложности N * M раз. Таким образом, общая сложность для двух петель равна O (N2).
Быстрый способ объяснить это - визуализировать его.
если оба я и J от 0 до N, легко видеть, O (N^2)
O O O O O O O O
O O O O O O O O
O O O O O O O O
O O O O O O O O
O O O O O O O O
O O O O O O O O
O O O O O O O O
O O O O O O O O
в данном случае, это:
O
O O
O O O
O O O O
O O O O O
O O O O O O
O O O O O O O
O O O O O O O O
Это выходит, чтобы быть 1/2 от N^2, который все еще равен O (N^2)
Спасибо, что помогли мне понять, как внутренние циклы с условием j <= i приводят к 1/2 N^2. Это беспокоило меня в течение некоторого времени. Можете ли вы объяснить, как это все еще O (N^2)? –
Из-за закона Мура мы можем предположить, что скорость выполнения алгоритма удваивается примерно каждые 18 месяцев. Из-за этого при анализе алгоритмов мы можем отбросить коэффициент и просто сосредоточиться на алгоритмах в терминах n. В основном O (n^2) возьмет O (1/2 n^2) через 18 месяцев. Так как n растет выше, время выполнения растет экспоненциально, где для линейного алгоритма времени он растет с n. –
Итак, что вы говорите, так это то, что при вычислении больших Ох обозначение 1/2 в 1/2 (n^2) несущественно, отчасти из-за того, что коэффициенты становятся неактуальными во времени? Важная часть этого термина - опять-таки, с точки зрения большого О - заключается в том, что он квадратичный, а не квадратичный, который уменьшается вдвое? –
На 1-й итерации внешнего контура (i = 1) внутренний цикл будет повторяться 1 раз На 2-й итерации внешнего цикл (я = 2), внутренний цикл будет итерации 2 раза На третьей итерации внешнего контура (i = 3) внутренний контур будет повторяться 3 раза
.
.
На последней итерации внешнего цикла (I = N), внутренний цикл будет итерации п раз
Таким образом, общее число раз операторы во внутреннем цикле будут выполняться будет равна сумма чисел от 1 до п, что:
((n)*n)/2 = (n^2)/2 = O(n^2) times
Дубликат http://stackoverflow.com/questions/362059/big-o-of-this-nested-loop –
Мой вопрос не совсем дубликат того, с которым вы связались, но это общий вопрос, поэтому я думаю, что его спрашивают во многих формах. – yyy
Связанный: [Как найти временную сложность алгоритма] (https://stackoverflow.com/q/11032015) – Dukeling