Современные нейросети умеют не только поддерживать диалог, но и писать код, причем с каждым годом они становятся всё умнее. Но какой ИИ-ассистент справляется с задачами программирования лучше остальных? Давайте разберемся!
Участники тестирования
Мы протестируем пять популярных нейросетей:
- YandexGPT – отечественная разработка, способная генерировать код и адаптировать его под задачи пользователя.
- GPT-4 – одна из самых мощных моделей OpenAI, широко используемая в разработке.
- Grok – нейросеть от X (бывшего Twitter) с фокусом на обработку запросов в реальном времени.
- Gigachat – модель от Сбербанка, активно развивающаяся в русскоязычном пространстве.
- DeepSeek – нейросеть, ориентированная на анализ данных и программирование.
Методология тестирования
Для честного сравнения мы предложим всем участникам три одинаковых теста. В каждом из них оценим корректность кода, его эффективность и читаемость. После получения ответов сравним коды и проверим их.
Тест 1: Реализация алгоритма
Задача: Написать функцию для сортировки списка чисел методом быстрой сортировки.
Критерии оценки:
- Корректность работы алгоритма
- Читаемость и лаконичность кода
- Производительность (если нейросеть предлагает нестандартные оптимизации, это будет плюсом)
Тест 2: Оптимизация кода
Задача: Оптимизировать предложенный неэффективный код, содержащий избыточные вычисления и дублирование.
numbers = [1, 2, 3, 4, 5]
result = []
for num in numbers:
if num % 2 == 0:
result.append(num * 2)
else:
result.append(num * 3)
print(result)
Критерии оценки:
- Улучшение читаемости кода
- Снижение избыточных вычислений
- Оптимизация по скорости выполнения
Тест 3: Генерация фронтенд-компонента
Задача: Написать React-компонент, который отображает кнопку с текстом "Нажми меня". При нажатии на кнопку должен появляться всплывающий алерт с текстом "Привет, мир!".
Критерии оценки:
- Соответствие требованиям задачи
- Чистота и понятность кода
- Использование современных практик React
Ну а теперь смотрим, кто что выдал.
Тест 1[YaGPT5]:
def quick_sort(arr):
if len(arr) > 1:
x = arr[len(arr) // 2] # опорный элемент
low = [u for u in arr if u < x]
eq = [u for u in arr if u == x]
hi = [u for u in arr if u > x]
arr = quick_sort(low) + eq + quick_sort(hi)
return arr
На этом все, коротко и по делу.
обратите внимание, тут есть даже кнопочка "Объяснить"
Нажал на кнопку:
Итак, код работает и сортирует.
Тест 1[GPT-4o]:
Вот реализация алгоритма быстрой сортировки на Python:
def quick_sort(arr: List[int]) -> List[int]:
if len(arr) <= 1:
return arr
pivot = arr[len(arr) // 2]
left = [x for x in arr if x < pivot]
middle = [x for x in arr if x == pivot]
right = [x for x in arr if x > pivot]
return quick_sort(left) + middle + quick_sort(right)
# Пример использования
if __name__ == "__main__":
sample_list = [3, 6, 8, 10, 1, 2, 1]
sorted_list = quick_sort(sample_list)
print("Отсортированный список:", sorted_list)
Вместо этого ответить в чате
Этот код:
- Корректно реализует алгоритм быстрой сортировки.
- Читаем и лаконичен, благодаря использованию списковых включений и рекурсивного подхода.
- Производителен, так как использует эффективный метод разделения списка на части.
Если нужна дополнительная оптимизация (например, переход на интроспективную сортировку или использование итеративного подхода для снижения затрат по памяти), можно обсудить! 🚀
Кроме решения, GPT предложил варианты использования и вообще немного пояснил.
Тест 1[Grok]:
Я реализую алгоритм быстрой сортировки (QuickSort) на Python, так как это популярный язык, а задача не указывает конкретный язык программирования. Реализация будет включать классический подход с выбором опорного элемента (pivot) и рекурсивным разделением массива.
Вот решение:
python
def quicksort(arr):
# Базовый случай: если массив пустой или из одного элемента
if len(arr) <= 1:
return arr
# Выбираем опорный элемент (в данном случае - средний)
pivot = arr[len(arr) // 2]
# Разделяем элементы на три группы
left = [x for x in arr if x < pivot] # Элементы меньше опорного
middle = [x for x in arr if x == pivot] # Элементы равные опорному
right = [x for x in arr if x > pivot] # Элементы больше опорного
# Рекурсивно сортируем подмассивы и объединяем
return quicksort(left) + middle + quicksort(right)
# Пример использования
if __name__ == "__main__":
test_list = [64, 34, 25, 12, 22, 11, 90]
sorted_list = quicksort(test_list)
print(f"Original list: {test_list}")
print(f"Sorted list: {sorted_list}")
Объяснение и оценка:
Корректность работы алгоритма:
Алгоритм использует классическую стратегию "разделяй и властвуй".
Опорный элемент (pivot) выбирается как средний элемент массива, что помогает избежать худшего случая при уже отсортированном массиве (в отличие от выбора первого или последнего элемента).
Разделение на три части (left, middle, right) корректно обрабатывает дубликаты, что важно для стабильности.
Читаемость и лаконичность кода:
Код написан в декларативном стиле с использованием списковых включений (list comprehensions), что делает его компактным и понятным.
Названия переменных (left, middle, right) интуитивно отражают их назначение.
Комментарии поясняют ключевые шаги.
Производительность:
Средняя временная сложность: O(n log n).
Худший случай: O(n²) при неудачном выборе опорного элемента, но выбор среднего элемента снижает вероятность этого.
Пространственная сложность: O(n) из-за создания новых списков.
Оптимизация: можно было бы реализовать сортировку "на месте" (in-place), изменяя исходный массив, чтобы уменьшить использование памяти. Однако это усложнит читаемость. Если нужна такая версия, могу предложить ниже.
Альтернативная версия (in-place):
Если важна производительность по памяти, вот вариант сортировки на месте:
python
def quicksort_inplace(arr, low, high):
def partition(low, high):
pivot = arr[high]
i = low - 1 # Индекс меньшего элемента
for j in range(low, high):
if arr[j] <= pivot:
i += 1
arr[i], arr[j] = arr[j], arr[i]
arr[i + 1], arr[high] = arr[high], arr[i + 1]
return i + 1
if low < high:
# Находим индекс опорного элемента
pi = partition(low, high)
# Рекурсивно сортируем подмассивы
quicksort_inplace(arr, low, pi - 1)
quicksort_inplace(arr, pi + 1, high)
return arr
# Пример использования
if __name__ == "__main__":
test_list = [64, 34, 25, 12, 22, 11, 90]
quicksort_inplace(test_list, 0, len(test_list) - 1)
print(f"Sorted list: {test_list}")
Сравнение:
Первая версия: более читаемая, лаконичная, но требует больше памяти.
Вторая версия: экономит память (O(log n) для стека вызовов), но сложнее для понимания из-за работы с индексами.
Если у вас есть предпочтения по языку или дополнительные требования (например, конкретные оптимизации), дайте знать!
Grok предложил два варианта и даже пояснил у какого варианта свои плюсы.
Тест 1[GigaChat]:
def quick_sort(arr):
if len(arr) <= 1:
return arr
pivot = arr[len(arr) // 2]
left = [x for x in arr if x < pivot]
middle = [x for x in arr if x == pivot]
right = [x for x in arr if x > pivot]
return quick_sort(left) + middle + quick_sort(right)
Пояснение:
Базовый случай: Если длина массива меньше или равна 1, возвращаем его как отсортированный.
Выбор опорного элемента: Выбираем средний элемент массива в качестве опорного (pivot).
Разделение массива: Разделяем массив на три части: элементы меньше опорного, равные опорному и больше опорного.
Рекурсивная сортировка: Рекурсивно сортируем левую и правую части массива и объединяем их с опорным элементом.
Производительность:
Средняя сложность: O(n log n)
Худший случай: O(n²) (если опорный элемент всегда оказывается максимальным или минимальным)
Оптимизации:
Можно улучшить производительность, выбирая опорный элемент более случайным образом (например, используя медиану из трех элементов).
Можно использовать вставку вместо рекурсии для небольших подмассивов (например, для массивов длиной меньше 10).
Как видим GigaChat тоже справился с простой задачей. И дал пояснения с рекомендациями.
Тест 1[DeepSeek]:
Для реализации алгоритма быстрой сортировки (quicksort) на Python можно использовать следующий код:
python
Copy
def quicksort(arr): if len(arr) <= 1: return arr
pivot = arr[len(arr) // 2] left = [x for x in arr if x < pivot] middle = [x for x in arr if x == pivot] right = [x for x in arr if x > pivot] return quicksort(left) + middle + quicksort(right)
# Пример использования arr = [3, 6, 8, 10, 1, 2, 1] sorted_arr = quicksort(arr) print(sorted_arr)
Объяснение:
- Базовый случай: Если длина списка меньше или равна 1, он уже отсортирован, и мы возвращаем его как есть.
- Выбор опорного элемента: В данном случае опорный элемент выбирается как средний элемент списка.
- Разделение списка: Список разделяется на три части:
left: элементы меньше опорного.
middle: элементы равные опорному.
right: элементы больше опорного. - Рекурсивный вызов: Функция вызывается рекурсивно для left и right, а затем результаты объединяются.
Критерии оценки:
- Корректность работы алгоритма: Алгоритм корректно сортирует список чисел.
- Читаемость и лаконичность кода: Код прост для понимания и лаконичен.
- Производительность: В среднем случае время выполнения алгоритма составляет O(n log n), что является оптимальным для сортировки.
Оптимизации:
- Выбор опорного элемента: В данном примере опорный элемент выбирается как средний элемент, что является простым и эффективным подходом. Однако можно использовать более сложные стратегии, такие как выбор медианы из трех элементов (первого, среднего и последнего), чтобы улучшить производительность в худших случаях.
- In-place сортировка: В данном примере создаются новые списки для left, middle и right, что может быть неэффективно по памяти. Можно реализовать in-place версию алгоритма, которая будет сортировать список на месте, не создавая новых списков.
Пример in-place реализации:
python
Copy
def quicksort_inplace(arr, low, high): if low < high: pivot_index = partition(arr, low, high) quicksort_inplace(arr, low, pivot_index - 1) quicksort_inplace(arr, pivot_index + 1, high)
def partition(arr, low, high): pivot = arr[high] i = low
for j in range(low, high): if arr[j] < pivot: arr[i], arr[j] = arr[j], arr[i] i += 1 arr[i], arr[high] = arr[high], arr[i] return i
# Пример использования arr = [3, 6, 8, 10, 1, 2, 1] quicksort_inplace(arr, 0, len(arr) - 1) print(arr)
Эта версия сортирует список на месте, что более эффективно по памяти.
В следующей статье рассмотри
Тест 2: Оптимизация кода
Задача: Оптимизировать предложенный неэффективный код, содержащий избыточные вычисления и дублирование.
numbers = [1, 2, 3, 4, 5]
result = []
for num in numbers:
if num % 2 == 0:
result.append(num * 2)
else:
result.append(num * 3)
print(result)
Критерии оценки:
- Улучшение читаемости кода
- Снижение избыточных вычислений
- Оптимизация по скорости выполнения
Итак, это был первый тест из трех. В следующих статьях проверим работу нейросетей на более интересных задачах.