Помогите с большой нотацией O

У меня были некоторые проблемы, пытаясь понять концепцию большой нотации O. Итак, по определению большой O выглядит следующим образом: T(n) ∈ O(G(n)) if T(n) <= G(n) * C.

Поскольку константа «C» может быть любым целым числом > 0, не будет ли верным и следующий пример?

Пример:

n log n ∈ O(log n)
n log n <= log n * c

Где C равно значению n.

Я знаю, что ответ таков, что n log n ∉ O(log n), но я не понимаю, как, поскольку C может быть любой константой.

Заранее спасибо за помощь :D


person Steven    schedule 27.07.2010    source источник
comment
@ Джейкоб, очевидно. Тем не менее, это не делает его плохим вопросом. bigO — это то, что должен понимать каждый программист.   -  person Byron Whitlock    schedule 27.07.2010
comment
Не домашняя работа, а просто уточнение кое-чего перед промежуточным экзаменом.   -  person Steven    schedule 27.07.2010
comment
@ Стивен, я бы хотел, чтобы у них были внутренние сети (особенно ТАК), когда я учился в колледже. Спасло бы меня от многих часов в подземелье (библиотека CS в подвале научного здания). Удачи на экзамене!   -  person Byron Whitlock    schedule 27.07.2010
comment
Спасибо, Байрон, и еще раз спасибо всем за такие замечательные ответы :D   -  person Steven    schedule 27.07.2010


Ответы (8)


c - это просто константа. Это означает, что вы не можете сказать «пусть c будет значением n», потому что вы должны сначала выбрать некоторое c, а затем разрешить сравнение для всех n.

Другими словами, чтобы некоторое T(n) было равно O(G(n)), не должно существовать никакой константы c такой, что G(n)*c больше, чем T(n) для всех н.

Таким образом, n log n не равно O(log n), потому что независимо от того, какую константу вы выберете, n > c приведет к тому, что n log n будет больше, чем c log n.

person Borealid    schedule 27.07.2010

Позвольте мне повторить ваши слова.

c может быть любой константой.

Это означает, что c не может зависеть от n.

person mik01aj    schedule 27.07.2010

идея состоит в том, что неравенство выполняется для любого n и фиксированного c. поэтому, хотя вы можете найти определенное c такое, что n log n ‹ c log n (а именно, любое c>n), вы можете легко найти другое n', для которого это не выполняется (а именно n'>c).

person Nicolas78    schedule 27.07.2010
comment
Я думаю, что причина этого недоразумения в том, что вы выбираете c в какой-то точке. Но это один раз на класс функций, а не один раз на n. - person Nicolas78; 28.07.2010

Прежде всего, если n=C, то C не является константой. И в большинстве реальных алгоритмов C мало, поэтому большая часть O обычно доминирует для типичных значений n.

Но сложность большого O связана с эффективностью алгоритма для больших n, особенно когда n приближается к бесконечности. Другими словами, он говорит вам о масштабируемости алгоритма: насколько хорошо данный алгоритм справляется с очень большой или удвоенной рабочей нагрузкой.

Если вы знаете, что n всегда мало, то сложность большого O не так важна, скорее вам следует сосредоточиться на времени настенных часов, требуемом алгоритмом. Кроме того, если вы выбираете между двумя алгоритмами, которые имеют одинаковую сложность большого O (например, O (n log n)), довольно часто один из них лучше, чем другой (например, быстрая сортировка со случайным сводом обычно превосходит сортировку двоичной кучи).

person Qwertie    schedule 27.07.2010
comment
в большинстве реальных алгоритмов c мала, поэтому большая часть O обычно доминирует для типичных значений n: это путает одну c — константу, используемую для определения того, что определенный алгоритм является O (чем-то) — с совершенно другим c , постоянный коэффициент времени выполнения программы (т.е. время выполнения=3X+c). Это не то же самое. - person Borealid; 28.07.2010
comment
OP использовал C в качестве мультипликативного фактора, а не постоянного добавленного члена. Я просто использовал тот же язык (извините за строчную с). - person Qwertie; 28.07.2010
comment
Это не то, что я имел ввиду. И, на самом деле, в исходном вопросе использовалась строчная буква «с». Прочитайте предложение, которое я выбрал очень внимательно, и вы увидите, что оно не может относиться к произвольной мультипликативной константе из сообщения ОП, потому что «с» ОП является выбранным контрпримером, а не фактором реального алгоритма. c мало в большинстве реальных алгоритмов относится к коэффициенту времени выполнения. - person Borealid; 28.07.2010
comment
@Borealid: Нет, я до сих пор понятия не имею, почему вы говорите о добавке +c. - person Qwertie; 11.04.2011
comment
Если алгоритм на n элементах выполняет n+k операций, это O(n). Способ, которым вы доказываете, что это O(n), заключается в том, что вы говорите, что не существует такого X, что Xn › j*(n+k) для всех n. Переменная, на которую вы *должны ссылаться, когда говорите, что в большинстве реальных алгоритмов C мало, является постоянным фактором реального времени выполнения (k выше). Это не может быть экзистенциальная переменная (X выше) или экзистенциальная константа (j), потому что они не существуют для реальных алгоритмов. Но вы говорите, что если n=C, то C не константа. Поэтому где-то в ваших первых двух предложениях вы путаетесь. - person Borealid; 12.04.2011

В определении вы должны определить C только по самим T и G. Вот что означает константа C. Поэтому C не должен зависеть от их ввода. Так что нельзя считать C = n

person Shayan    schedule 27.07.2010

в выражении n log n нельзя сравнивать внешний n с C, как вы это делаете. Это все равно, что взять алгебраическое выражение x(x+1) и заменить один из x константой.

В n log n n является переменной. В большом выражении O C является константой.

person hvgotcodes    schedule 27.07.2010

Значение n зависит от входного набора, значение C фиксировано.

Так что да, если n = 16 и C = 256, это выглядит как n^2 * lg(n) для небольшого набора входных данных. Теперь увеличьте входной набор до 100 000 000; значение C остается равным 256, теперь у вас есть 256 * lg (100 000 000)

person BrianH    schedule 27.07.2010

Всякий раз, когда я застреваю на большом-о, я считаю полезным думать об этом как о соревновании: я выбираю большую-о-функцию (то есть, в вашем случае, logn) и константу (c). Важно то, что я должен выбрать реальное значение. Я обычно беру тысячу, просто так. Затем я должен позволить моему заклятому врагу выбрать любое n, которое он выберет. Обычно он выбирает миллиард.

Потом делаю сравнение.

Чтобы закончить пример, 10 ^ 9 * (log (10 ^ 9)) теперь явно намного больше, чем 1000 log (10 ^ 9). Таким образом, я знаю, что большое-о не сработает.

person agorenst    schedule 27.07.2010