Текущая реальность и будущие возможности кодирования на основе ИИ
11 марта 2023 г.Многие люди открыли для себя возможности ChatGPT в области генерации кода. Но насколько хорошо он на самом деле работает, и есть ли альтернативы? В этом посте я рассмотрю некоторые сценарии, в которых ИИ может помощь в написании кода и степень ее полезности. Наконец, я делаю все возможное, чтобы оценить его производительность.
Введение
За последние несколько месяцев ChatGPT был повсюду. Читать и слышать о том, как люди используют его и «заставляют» его делать ошибки, было весело в течение недели или двух, но это становится утомительным. По какой-то причине в моей ленте LinkedIn до сих пор есть хотя бы одна запись «Посмотрите, как произошел сбой ChatGPT» каждый день, и я не знаю, что люди пытаются этим доказать.
В то же время меня озадачивают заявления разработчиков программного обеспечения о том, что они используют ChatGPT для выполнения своей работы. Утверждения типа "На этой неделе я не написал ни строчки кода и использовал только ChatGPT" даже попали в подкасты, где люди обсуждали, какие рабочие места ИИ может заменить в будущем.
Для всех, кто серьезно работал разработчиком программного обеспечения, очевидно, что ИИ не сможет заменить разработчиков программного обеспечения в ближайшее время. Да, ChatGPT может генерировать код по заданному описанию проблемы, но он не годится для решения проблем, что является основной задачей инженера-программиста. Однако ИИ может выполнять определенные задачи, и я рассматриваю несколько примеров в этом посте.
Парное программирование AI
Некоторые сервисы реализуют интеллектуальное завершение кода, также называемое парным программированием ИИ. Этот термин вводит в заблуждение и, вероятно, был придуман кем-то, не имевшим большого опыта парного программирования. В то время как парное программирование особенно полезно, когда два человека работают вместе, чтобы обсудить, как что-то должно быть реализовано, ИИ GitHub Copilot и Tabnine. GitHub Copilot основан на OpenAI Codex, модель преобразования естественного языка в код на основе GPT-3. Согласно статье исследователей OpenAI, модель генерировала рабочий код для заданных строк документации Python более чем в 70% попыток. Это впечатляет, но также подчеркивает, что для получения хороших результатов требуются базовые навыки кодирования (например, написание строки документации). Как и ChatGPT, CodeX также можно использовать на веб-сайте OpenAI бесплатно.
Я уже давно использую Copilot для частных проектов, и он мне очень нравится. В начале (когда он был еще в техническом превью) он в основном копировал строки из кода GitHub. С тех пор он значительно улучшился и эволюционировал. Особенно для кода, который реализует общие задачи (например, вычисления или преобразования), существует высокая вероятность того, что Copilot предложит полную функцию на основе строки документа. Например, когда вы пишете def reverse(self, x:int) -> int...
будет предложена полная функция, включая возвращаемое значение.
Copilot также хорошо подходит для написания тестов. Просто добавьте имя «тест» к заданному имени функции, и она сделает свою работу.
Напротив, Tabnine стал для меня огромным разочарованием и показался мне глупым автодополнением, предлагающим в основном бесполезный или неправильный код. В то время как Copilot использует одну большую модель, Tabnine основан на нескольких более мелких моделях, решающих отдельные задачи. Возможно, поэтому удобнее использовать Tabnine в локальном режиме и обучать его собственным кодом (что невозможно с Copilot).
Даже с большим количеством контекста и хорошо названными переменными предложения, которые я получил от Tabnine, часто были далеки от того, что вы ожидали. Используя локальный режим, он хорошо работал в больших репозиториях с большим количеством похожего кода. Но это слишком просто по сравнению с проблемами, которые, как я ожидаю, решит такая модель. Это не было умным, но больше походило на инструмент для автоматического копирования и вставки.
Могут быть и другие случаи использования и обстоятельства, при которых Tabnine работает хорошо (например, в огромных базах кодов компаний, где все написано в одном стиле и на одном языке), но для человека, работающего над множеством небольших проектов, он просто не сработал. я.
Попросить ИИ написать код
Как упоминалось во введении, одним из основных вариантов использования ChatGPT является генерация кода. Конечно, это уже было возможно с CodeX, но бум ChatGPT заставил гораздо больше людей узнать о том, что это возможно. По сравнению с плагинами, упомянутыми ранее, этот подход направлен на перевод текстовых описаний проблем в код, а не на интеграцию в существующую кодовую базу.
Выполнение этой задачи для модели является сложной задачей, поскольку оно включает в себя понимание проблемы и создание подходящего функционального кода, который решает эту проблему. В прошлом многим моделям не удавалось надежно выполнить первое, и даже с более специализированными моделями это по-прежнему представляет собой серьезную проблему, которую ChatGPT не решает. Однако давайте посмотрим на код, который генерирует ChatGPT.
Запрос ChatGPT на создание приложения погоды
Я попросил ChatGPT написать приложение Streamlit, которое извлекает данные о погоде для Дортмунда из бесплатного API и отображает их на диаграмме.
Вот что у меня получилось:
import streamlit as st
import requests
import pandas as pd
import plotly.express as px
# Set up OpenWeatherMap API key
api_key = "YOUR_API_KEY_HERE"
# Define function to get weather data from OpenWeatherMap API
def get_weather_data():
url = f"https://api.openweathermap.org/data/2.5/onecall?lat=51.5134&lon=7.4814&exclude=hourly,minutely&appid={api_key}&units=metric"
response = requests.get(url)
data = response.json()
return data
# Get weather data
data = get_weather_data()
# Convert weather data to a Pandas DataFrame
df = pd.DataFrame(data["daily"])
# Format the date column
df["dt"] = pd.to_datetime(df["dt"], unit="s")
df["date"] = df["dt"].dt.date
df = df.set_index("date")
# Create a line chart using Plotly Express
chart = px.line(df, x=df.index, y="temp.day", title="Dortmund Weather Forecast")
chart.update_xaxes(title="Date")
chart.update_yaxes(title="Temperature (°C)")
# Display the chart in the Streamlit app
st.plotly_chart(chart)
В общем, это не так уж и плохо.
ChatGPT также дал несколько инструкций о том, как получить ключ API. К сожалению, мне не сказали, что я также должен установить plotly
, но поскольку я попросил приложение Streamlit, можно предположить, что я знаю, как устанавливать библиотеки.
Тем не менее, есть две проблемы:
- Значение температуры анализируется неправильно. Он сохраняется как словарь, и доступ к нему с помощью
y="temp.day"
вызовет ошибку. Быстрое и простое решение — заменить это наy=df['temp'].str['day']
. Я предполагаю, что это хороший пример того, как модель изучила множество различных способов обработки ответов API, но не смогла установить связь между синтаксическим анализом данных и повторным доступом к ним для диаграммы.
* Приложение работает только при наличии действительного ключа API и выдает ошибку, если его нет. Отсутствующая обработка ошибок вызывает сожаление, поскольку она отображает сообщения об ошибках во внешнем интерфейсе. Однако это можно быстро исправить, перехватив ошибку и отобразив ее в более удобном для пользователя виде
сообщение (предпочтительно) или реализация вызова API, чтобы ошибка не отображалась в пользовательском интерфейсе.
Помимо этих проблем, код выглядит нормально и работает после исправления первой проблемы. Кроме того, хотя в целом количество комментариев может быть слишком большим, полезно разобраться в сгенерированном коде.
Написание тестов с помощью ChatGPT
Затем я попросил ChatGPT написать модульный тест для приложения.
import unittest
from app import get_weather_data
class TestWeatherApp(unittest.TestCase):
def test_weather_data(self):
# Call the function to get weather data
data = get_weather_data()
# Check that the data contains the expected keys
self.assertIn("current", data)
self.assertIn("hourly", data)
self.assertIn("daily", data)
# Check that the daily data contains the expected keys
daily_data = data["daily"][0]
self.assertIn("dt", daily_data)
self.assertIn("temp", daily_data)
self.assertIn("feels_like", daily_data)
self.assertIn("pressure", daily_data)
self.assertIn("humidity", daily_data)
self.assertIn("dew_point", daily_data)
self.assertIn("wind_speed", daily_data)
self.assertIn("wind_deg", daily_data)
self.assertIn("weather", daily_data)
self.assertIn("clouds", daily_data)
self.assertIn("pop", daily_data)
self.assertIn("uvi", daily_data)
Это интересно.
Во-первых, тест вызывает get_weather_data(), но ключ API определяется вне функции. Поэтому он будет работать без ключа API и всегда будет давать сбой. Так что тест бесполезен. Кроме того, это не модульный тест, а интеграционный тест. Он проверяет, возвращает ли (внешний) API правильные данные. Чтобы реализовать модульный тест, ожидаемые данные должны быть имитированы, поэтому я попросил ChatGPT исправить это.
<цитата>Это не модульный тест, а интеграционный тест. Вы можете это исправить?
import unittest
from unittest.mock import patch
from app import get_weather_data
class TestWeatherApp(unittest.TestCase):
@patch('requests.get')
def test_get_weather_data(self, mock_get):
# Set up test data
expected_data = {'daily': [
{'dt': 1645808400,
'temp': {'day': 5.5, 'min': 2.15, 'max': 7.9, 'night': 3.4, 'eve': 7.9, 'morn': 2.15},
'feels_like': {'day': 0.3, 'night': -3.04, 'eve': 4.06, 'morn': -4.01},
'pressure': 1028, 'humidity': 51, 'dew_point': -2.57, 'wind_speed': 2.81, 'wind_deg': 194,
'weather': [{'id': 801, 'main': 'Clouds', 'description': 'few clouds', 'icon': '02d'}],
'clouds': 16, 'pop': 0, 'uvi': 2.21}],
'timezone_offset': 3600}
# Set up mock response from requests.get
mock_response = type(
'MockResponse',
(object,),
{'json': lambda self: expected_data}
)
mock_get.return_value = mock_response
# Call the function to get weather data
data = get_weather_data()
# Check that the function returns the expected data
self.assertEqual(data, expected_data)
Это выглядит намного лучше, но все же мне не хватает тестирования на возможные случаи ошибок, поэтому я спросил еще раз:
<цитата>Разве модульный тест не должен также проверять, не падает ли приложение, если происходит что-то необычное. Например, если API не работает?
ChatGPT добавил эту часть в сгенерированный ранее код:
@patch('requests.get')
def test_get_weather_data_error(self, mock_get):
# Set up mock response from requests.get to raise an exception
mock_get.side_effect = Exception("Connection error")
# Call the function to get weather data
with self.assertRaises(Exception):
data = get_weather_data()
Это дополнение выглядит разумным. Однако, поскольку исходное приложение не обрабатывает никаких случаев ошибок, этот тест не имеет особого смысла. Проверка того, не падает ли приложение, когда мы знаем, что оно произойдет, ни к чему не приводит, поэтому я перестал спрашивать.
В целом, результаты, представленные ChatGPT, были удовлетворительными. Они, безусловно, помогают с прототипированием или дают шаблон для начала. Тем не менее, код все еще должен быть готов к работе. ChatGPT, безусловно, поможет в этом, но постепенно улучшать код, задавая правильные вопросы, — неэффективный способ работы.
Перспективы
В прошлом году программа Deepmind AlphaCode приняла участие в соревнованиях по программированию и показала себя как средний человек-конкурент Код и некоторые комментарии человека-конкурента можно найти здесь. Это был настоящий прорыв, поскольку впервые модель кодирования ИИ доказала способность решать проблемы. Будет интересно посмотреть, как эти модели улучшатся и найдут применение в разработке программного обеспечения.
Также опубликовано здесь.
Оригинал