Go + AI: можно ли обойтись без Python в машинном обучении?
Считаете, что Python — единственный путь в машинное обучение? Go может вас удивить! Разбираем, как использовать Go для inference моделей, создания ML-микросервисов и обработки данных. Узнайте, когда Go работает лучше Python, какие библиотеки использовать и как комбинировать оба языка для максимальной эффективности.
Почему вообще рассматривать Go для ML?
Python — отличный язык для прототипирования и исследований, но у него есть свои ограничения:
Производительность: Python медленный, особенно без оптимизированных библиотек
Параллелизм: GIL (Global Interpreter Lock) усложняет многопоточность
Развертывание: упаковка Python-приложений с зависимостями — та еще задача
Типизация: динамическая типизация может приводить к ошибкам в продакшене
Go решает многие из этих проблем:
Компилируемый язык с высокой производительностью
Встроенная поддержка конкурентности через горутины
Один бинарный файл без зависимостей
Статическая типизация
Что можно делать на Go в области ML?
1. Inference (применение готовых моделей)
Самый популярный сценарий — использование уже обученных моделей. Вы обучаете модель в Python, а затем используете её в production на Go.
Пример с ONNX Runtime:
package main
import (
"fmt"
onnxruntime "github.com/yalue/onnxruntime_go"
)
func main() {
// Загружаем модель, обученную в PyTorch/TensorFlow
session, err := onnxruntime.NewSession[float32](
"model.onnx",
[]string{"input"},
[]string{"output"},
nil,
)
if err != nil {
panic(err)
}
defer session.Destroy()
// Подготавливаем входные данные
input := []float32{1.0, 2.0, 3.0, 4.0}
// Делаем предсказание
output, err := session.Run([][]float32{input})
if err != nil {
panic(err)
}
fmt.Println("Prediction:", output[0])
}2. Классические ML-алгоритмы
Для многих задач не нужны нейросети. Линейная регрессия, решающие деревья, k-means — всё это можно реализовать на Go.
Библиотека GoLearn:
package main
import (
"fmt"
"github.com/sjwhitworth/golearn/base"
"github.com/sjwhitworth/golearn/evaluation"
"github.com/sjwhitworth/golearn/knn"
)
func main() {
// Загружаем данные
rawData, err := base.ParseCSVToInstances("data.csv", true)
if err != nil {
panic(err)
}
// Создаем классификатор KNN
cls := knn.NewKnnClassifier("euclidean", "linear", 2)
// Разделяем на train/test
trainData, testData := base.InstancesTrainTestSplit(rawData, 0.7)
// Обучаем
cls.Fit(trainData)
// Проверяем точность
predictions, err := cls.Predict(testData)
if err != nil {
panic(err)
}
confusionMat, err := evaluation.GetConfusionMatrix(testData, predictions)
if err != nil {
panic(err)
}
fmt.Println(evaluation.GetAccuracy(confusionMat))
}3. Обработка данных и feature engineering
Go отлично подходит для ETL-пайплайнов и обработки больших объемов данных.
package main
import (
"encoding/csv"
"os"
"strconv"
"sync"
)
type DataPoint struct {
Feature1 float64
Feature2 float64
Label int
}
func processData(filename string) ([]DataPoint, error) {
file, err := os.Open(filename)
if err != nil {
return nil, err
}
defer file.Close()
reader := csv.NewReader(file)
records, err := reader.ReadAll()
if err != nil {
return nil, err
}
// Параллельная обработка через горутины
var wg sync.WaitGroup
results := make([]DataPoint, len(records)-1)
for i, record := range records[1:] {
wg.Add(1)
go func(idx int, rec []string) {
defer wg.Done()
f1, _ := strconv.ParseFloat(rec[0], 64)
f2, _ := strconv.ParseFloat(rec[1], 64)
label, _ := strconv.Atoi(rec[2])
// Нормализация или другие преобразования
results[idx] = DataPoint{
Feature1: (f1 - 50) / 10,
Feature2: (f2 - 100) / 20,
Label: label,
}
}(i, record)
}
wg.Wait()
return results, nil
}4. Микросервисы для ML
Go идеален для создания API, которые обслуживают ML-модели:
package main
import (
"encoding/json"
"net/http"
"log"
)
type PredictionRequest struct {
Features []float64 `json:"features"`
}
type PredictionResponse struct {
Prediction float64 `json:"prediction"`
Confidence float64 `json:"confidence"`
}
func predictHandler(w http.ResponseWriter, r *http.Request) {
var req PredictionRequest
if err := json.NewDecoder(r.Body).Decode(&req); err != nil {
http.Error(w, err.Error(), http.StatusBadRequest)
return
}
// Здесь вызываем вашу модель
prediction := runModel(req.Features)
response := PredictionResponse{
Prediction: prediction,
Confidence: 0.95,
}
w.Header().Set("Content-Type", "application/json")
json.NewEncoder(w).Encode(response)
}
func runModel(features []float64) float64 {
// Ваша логика inference
return 42.0
}
func main() {
http.HandleFunc("/predict", predictHandler)
log.Println("Server starting on :8080")
log.Fatal(http.ListenAndServe(":8080", nil))
}
Популярные Go-библиотеки для ML
Gorgonia — библиотека для построения нейронных сетей, похожа на PyTorch
GoLearn — классические ML-алгоритмы
Gonum — численные вычисления (аналог NumPy)
ONNX Runtime Go — запуск моделей ONNX
TensorFlow Go — Go-биндинги для TensorFlow
Когда использовать Go, а когда Python?
Используйте Go когда:
Нужна высокая производительность в production
Важна легкость развертывания (один бинарник)
Работаете с конкурентными нагрузками
Используете готовые модели (inference)
Строите ML-микросервисы
Оставайтесь с Python когда:
Проводите исследования и эксперименты
Обучаете сложные нейросети
Нужен богатый выбор библиотек
Работаете с командой data scientists
Самый практичный вариант:
Python для обучения моделей, экспериментов, data science
Go для production-окружения, API, обработки данных
Такой подход использует сильные стороны каждого языка.
Практический пример: рекомендательная система.
package main
import (
"math"
"sort"
)
type Item struct {
ID int
Features []float64
}
type Recommendation struct {
ItemID int
Score float64
}
// Косинусное сходствоfunc cosineSimilarity(a, b []float64) float64 {
var dotProduct, normA, normB float64
for i := range a {
dotProduct += a[i] * b[i]
normA += a[i] * a[i]
normB += b[i] * b[i]
}
return dotProduct / (math.Sqrt(normA) * math.Sqrt(normB))
}
// Получаем рекомендацииfunc getRecommendations(userPrefs []float64, items []Item, topN int) []Recommendation {
recommendations := make([]Recommendation, len(items))
for i, item := range items {
recommendations[i] = Recommendation{
ItemID: item.ID,
Score: cosineSimilarity(userPrefs, item.Features),
}
}
// Сортируем по score
sort.Slice(recommendations, func(i, j int) bool {
return recommendations[i].Score > recommendations[j].Score
})
return recommendations[:topN]
}
func main() {
userPrefs := []float64{0.8, 0.3, 0.9}
items := []Item{
{ID: 1, Features: []float64{0.9, 0.2, 0.8}},
{ID: 2, Features: []float64{0.1, 0.9, 0.2}},
{ID: 3, Features: []float64{0.7, 0.4, 0.9}},
}
recs := getRecommendations(userPrefs, items, 2)
// Выведет топ-2 рекомендации
}Заключение
Go вполне может использоваться для построения ML-систем, особенно в production-окружении. Да, для обучения сложных моделей Python остается стандартом, но для inference, обработки данных и создания высокопроизводительных сервисов Go — отличный выбор.
Выбор инструмента всегда зависит от задачи. Не нужно отказываться от Python полностью, но и не стоит игнорировать возможности Go в области ML.
Это и много другое можно изучить в Кодике — разобрать всё подробно и закрепить практикой с реальными заданиями. Мы предлагаем структурированные курсы по Python, Go, JavaScript и другим языкам с акцентом на практическое применение.
А если нужна поддержка и хочется обсудить код с единомышленниками — у нас уже больше 2000 активных разработчиков в Telegram-канале, где всегда помогут, подскажут и поддержат на пути изучения программирования!
🚀 Присоединяйтесь к сообществу разработчиков в Кодике!