Pull to refresh

Comments 123

А вы смотрели в сторону Erlang? Если да, то интересно ваше мнение.

Кажется, что Erlang бы тут подошел ничуть не хуже, чем Go. Erlang компилируемый и асинхронный. Учится вряд ли дольше, чем Go. Да он динамически типизирован, но предусмотрены спеки, которые как раз позволяют не писать тесты на тривиальные кейсы.
К сожалению, я достаточно поверхностно знаком с Erlang, не могу ничего сказать по этому поводу.
Есть множество причин, по которым не использовался Erlang. Но самая главная — это время поиска людей, которые бы хотели/могли писать на Erlang. Даже Ericsson, создатель Erlang теперь пишет на Go =)
В Ericsson пишут на большом количестве различных языков, я бы не сказал, что Erlang там основной.
Это понятно, в огромной корпорации есть место любым извращениям. Я о другом, для некоторых задач Go подходит лучше, например для управления облаками.
OpenStack вполне себе неплохо бегает на Python, или я просто немного не понимаю, о чем вы.
К сожалению, я не имел опыта разворачивания и управления OpenStack. Но я могу рассказать чем Go лучше Python.
Точно так же, как и чем Python лучше Go =)
Когда любишь, то уже не замечаешь недостатков =)
Я к тому, что и там и там они есть.
Да, согласен, в Go куча недостатков, они у меня все записаны в отдельный блокнот.
Оформите это в статью. Интересно почитать будет.
Хорошо, я попробую. Но наверное это будет скорее об «особенностях», чем недостатках =)
Напомнило из какого-то фильма: «Это доказывает, что Бога не существует… Если господин пожелает, я могу доказать обратное.»
Я сейчас пишу и на том, и на том; к Go у меня смешанные чувства. Пока что я его вижу как отличный язык для написания небольших демонов, работающих с сетью. В остальных отношениях от него постоянно возникает неприятное ощущение недоделанности, непродуманности какой-то, даже не знаю, как лучше выразиться.

По уровням абстракции он очень несбалансированный: например, сопрограммы реализованы довольно хорошо и удобно, а вот кроссплатформенное получение кода возврата от процессов, запущенных через exec.Command, уже заставляет писать несколько файлов под разные ОС. Довольно простая работа с http, но какая-нибудь другая область применения — и вот уже танцуешь с syscall. Обрабатываешь очередной назойливый err, и кажется, что просто взяли старый-добрый C, и натянули на него какое-то хипстерское шмотье.

Никак не могу отделаться от ощущения, что это какой-то DSL для написания всяких сетевых штук.
Я вас понимаю, Go действительно скорее недоделан, чем переделан. И многое в нём навязывается. Но он развивается очень быстро, в том числе и силами уже не маленького сообщества, которое очень отзывчиво. Возможно для ваших задач нужно что-то уже более зрелое и выразительное.
Я не знаком (пока) с Go, поэтому хочется спросить — а почему неудобность api это проблема Go?

В нём не принято использовать библиотеки?
Ну взять (или написать) либу с другим exec.command, впихать туда те несколько файлов под разные ОС, выложить в публичный репозиторий чтбоы подключалась к проекту одной строчкой.

Если проблема только в наличии библиотек, то не язык виноват, а просто готовых библиотек нету, не?
Эта проблема, безусловно, решается, но все-таки хотелось бы иметь продуманную полноценную стандартную библиотеку. Сейчас она хороша только пока вы работаете с сетью, в остальном складывается ощущение, будто написана довольно хаотично и «чтобы было». Если посмотреть tech talk об истории языка, то не возникает ощущения, будто над многими вещами там и правда заморачивались.

Сторонние библиотеки пока сыры и плохо документированы. Обычные библиотеки документированы лучше, но чаще всего приходится лезть в исходники, чтобы понять, как оно на самом деле работает (например, редко когда по документации можно понять, как разобрать ошибку из кортежа). Но это — теоритически — еще можно поправить. А вот чего нельзя поправить, так это то, что со своими структурами зачастую нельзя работать как с теми, что идут вместе с языком. Хороший пример — это итерация.

В Go 4 разных синтаксиса для определения цикла for. Если вы итерируете стандартный срез, массив или мэп, то все ок. Но вот использовать те же конструкции для своих структур уже вряд ли получится.

Давайте пример:

type TreeNode struct {
	Value interface{}
	Left  *TreeNode
	Right *TreeNode
}

type BinaryTree struct {
	Root *TreeNode
}


Думаю, понятно, что здесь происходит. Структуры определили, давайте теперь попробуем прицепить к ним методы, чтобы можно было делать вот так:

for node := range tree.InOrder() {
	fmt.Println(node)
}

for node := range tree.PreOrder() {
	fmt.Println(node)
}


Думаю, понятно, что здесь должно происходить. Так вот, так делать нельзя. Вы не можете использовать range таким образом. Приходится явным образом доставать итератор и итерировать его вот так:

iterator := tree.PreOrderIterator()
for iterator.HasNext() {
	fmt.Println(iterator.Extract())
}


Или функция make. Отличная функция, инициализирующая неявные структуры, с которыми работают срезы или словари. О, мы только что написали свою суперкрутую структуру, довольно сложную в инициализации, хочется создавать ее тем же образом, что и тот же словарь (например, написали свой Set). Ничего подобного сделать нельзя.

Поэтому со всеми бибилиотеками контейнеров не получится работать всеми средствами языка, инициализировать аналогичным с теми же срезами или картами образом не получится. И это только один пример. А ведь еще есть отсутствие генериков, принуждающее (!!!) копипастить, еще есть абсолютно наколеночный go get, про который во времена PyPI, Gem'ов или npm'ов вообще говорить стыдно.

Какое в Go стандартное средство для dependency management'а? Так ведь нет его фактически. Роб Пайк сказал, что им и этого хватает, пускай коммьюнити пишет. Комьюнити написало Godep, GPM, еще какие-то поделки есть. Но единого способа, единообразной экосистемы в Go просто не существует. Зато есть вот такой костылина.
Подпишусь под каждым словом. Именно невозможность сделать что-то типа __iter__ в Python одна из вещей, которая мне в Go не нравится.
Вот за это __govna_piroga__ я и не люблю Python. Уверен, не я один. С моей точки зрения зарезервированных имён методов быть не должно. Имя функции — это полностью дело программиста. Имя не должно само по себе влиять на семантику, это просто идентификатор. По мне, так лучше ввести дополнительные ключевые слова-модификаторы, чем писать вот такое.
Ну давайте еще С++ поругаем за перегрузку операторов…
А я и ругаю и считаю перегрузку злом, делающим код совершенно не читаемым. Но речь не о том. Сама функция-оператор в C++ описывается достаточно изящно, а не костылями типа __rshift__ и __plus__ для
«зарезервированных имён методов быть не должно» — oh, really? Скажите это C++ кодерам с их вездессущим int main(). Зарезервированное имя функции? Да. Все привыкли и уже перестали обращать внимание на «неудобства» (которых нет)? Да. Абсолютно то же самое и в Python.
Это не неудобство, просто не эстетично.
А чем Go лучше? В нем для реализации интерфейсов достаточно всего-навсего иметь методы с теми же сигнатурами. И все, считается, что структура реализует интерфейс. То есть никаких дополнительных телодвижений не нужно. Просто считайте, что наличие __iter__, например, говорит о том, что класс теперь Iterable. В этом случае, так как и там, и там в отношении подобных вещей duck typing, разницы принципиальной нет.
Как я понимаю, философия создателей языка состоит в том, чтобы «не перегружать».

Да, очень много придумано в современных языках, но как я читал, они хотят оставить все настолько простым, насколько возможно, поэтому каждая новая фишка долго и тщательно продумывается.

Возможно в будущем это все введут, а на данный момент есть что есть.

Я сейчас полностью пишу на Go и знаю, как не хватает многих вещей, но в тоже время это каким-то странным образом позволяет решать задачи более простыми и элегатными способами, не создавая лишних «сущностей».
Не могу согласиться. go get настолько непродуман, что сообщество изобретает велосипеды один офигительнее другого. Зачем-то есть разница между работой со срезами (фундаментально, та же структура из интов), картами (тоже представляется в виде структуры) и своими struct'ами. Библиотеки для работы с текстом наводнены разными Do и DoString. Генерики имеют все шансы повторить историю своих «коллег» из Java. Мне сложно согласиться, что он тщательно продумывается, стандартная библиотека хоть и большая, но крайне неоднородная, часто приходится делать такие вещи, которые в 2014 уже не ожидаешь от нового языка.

А про недостаток синтаксического сахара: мой болевой порог тоже позволяет писать на Go, но при этом я не могу отделаться от мысли, что такая простота «хуже воровства».
for node := range tree.PreOrder() {
fmt.Println(node)
}

Так сделать можно. Если нет необходимости прервать итерирование в процессе — верните канал и поднимите горутину, которая будет в этот канал по одному объекту класть.

Впрочем для таких случаев я бы скорее написал что нибудь а-ля tree.foreach.
Безусловно, сделать так, чтобы формально код заработал, несложно. Можно вернуть канал, можно вернуть срез. Я не про то: большая часть методов языка работает с интерфейсами. Использовать такой интерфейс, чтобы можно было итерировать свой объект нельзя. Использовать такой интерфейс, чтобы можно было, грубо говоря, использовать [] тоже. Квадратные скобки де-факто введены только для срезов и словарей. Интерфейс для работы с make отсутствует.

В языке есть несколько хороших средств, но их можно использовать только с заранее определенным набором сущностей, от этого возникает стойкое ощущение неконсистентности. Можно сказать, что да, есть примитивы, есть структуры, вот вам примитивы, определяйте свои структуры и используйте структуры как вам угодно. Но, черт побери, это же встроенные возможности языка.

Если бы язык был консистентный, то там был бы примитив, который можно итерировать, и работали бы с ним как с данностью. Все. Это было бы нормально. И массивы бы итерировали с помощью какого-нибудь .At(index int), и из словаря бы брали с помощью .Get(key interface{}). Язык был бы шумный, но не возникало бы подобного вопроса.
По поводу «неконсистентный» я даже спорить не буду, благо ровно тем-же самым словом не так давно этот язык и описывал.
Правда по другой причине (работа с каналами, возврат нескольких значений из функции), но ощущение такое-же.
По поводу make и range. Насколько я могу судить, изначальная идея была не вводить в язык синтаксический сахар, завязанный на пользовательские интерфейсы. С другой стороны, разработчики не хотели делать встроенные объекты собственно объектами с методами. Объекты и интерфейсы находятся как бы уровнем выше, вне ведения базовых конструкций. Отсюда и такое поведение.
Я думаю подошел бы идеально, как разработчик на Erlang говорю:)
В середине статьи решил, что напишу комент про Erlang, но первый камент к статье уже был про Erlang =(

Поэтому приведу видео:
www.youtube.com/watch?v=jYrHjS8Z_XU
Интересно узнать, почему не рассматривали Java? Тем более, что Java в Яндексе давно применяется.

Судя по тестам от benchmarksgame.alioth.debian.org, Java работает несколько быстрее Go.
Вообще именно в нашем отделе java традиционно не использовали и этот вопрос как-то особенно не рассматривался. :)
Java действительно кажется не медленнее чем Go по тестам и по моим собственным воспоминаниям о работе с ней, имеет обширную стандартную библиотеку и много сторонних либ. Из недостатков по сравнению с Go можно отметить отсутствие lightweight threads из коробки и очень большой memory footprint одного запущенного инстанса, что для облачного приложения может быть критично. Еще один правда незначительный недостаток, то что нужно тащить за собой java runtime, на выходе у Go же получается статически слинкованный бинарник зависящий только от libc.
По lightweight threads в java есть akka, которая ну ни чуть не менее популярная чем гоу как платформа, особенно ели брать скала, где мало какое приложение сервереное работает без него, и есть quasar.
akka это всё-таки не lightweight threads, а тред пул с тяжеловесными тредами. Разница, например, в том, что нельзя залокаться в середине обработки сообщения на IO — надо освобождать тред
После Java захочется Scala, а Scala нельзя =)
А почему Scala нельзя, если не секрет?
Не секрет, язык не простой, сложно искать людей.
По секрету могу сказать вам, что некоторые небольшие штуки в Яндексе пишутся и на Scala.
Да, кто-то даже на racket, но я говорю про команду хотя бы из 5 человек. Я знаю многих, кто хотел бы писать на Scala, но пока не получается.
Я писал даже коммерческий сайт на Scala и больше всего бился головой об sbt.
Вот реально не могу понять, что там сложного? Наоборот все просто и очевидно… Ну да, синтаксис немного другой.

P.S. Вот почему никто не жалуется, что C# сложный? Ведь он содержит больше language-фич, чем скала, имхо. А на нем пишет примерно столько же людей, сколько и на джаве… Неужели никто не ропщет только потому, что выбора толком нет?
Позвольте поинтересоваться как вам удается иметь
regionId := region.GetRegionByLbs(req, this.lbs, this.geobase) асинхронным?
Мне чтобы добиться асинхроности приходиться передавть в функцию chan
и ожидать результата с помощью select.
Спасибо.
Ну, может он внутри создает кучу потоков, но результат синхронизирует, так что снаружи метод выглядит синхронным.
Этот метод внутри себя обращается к сервису Кокаина через go-framework. А обращения к нему как раз реализованы через channels. То есть управление останавливается там, где оно доходит до чтение из канала фреймворка и, как только он записывает туда ответ, исполнение продолжается.
«управление останавливается» звучит для меня как синхронный подход! ;)
В любом случаем большое спасибо, Кокаин один из лучших framework с которым
я знаком, есть повод глянуть на его Go библиотеку.
В фреймворке Go Кокаина не все идеально сейчас, мы планировали серьезный рефакторинг в ближайшее время. Он работает хорошо и надежно, но код и интерфейсы стоило бы причесать, плюс добавить тестов. Но посмотреть, конечно, можно :) github.com/cocaine/cocaine-framework-go
Нормальный (рабочий) пакетный менеджер для Go, который позволяет брать из гита определённые коммиты библиотек, уже запилили?
А почему не нода, например? Из-за динамической типизации?
Производительность ноды примерно на уровне питона или даже ниже, плюс проблемы с утечками памяти.
Зачем шило на мыло менять? :)
Можно множество бенчмарков в интеренете найти, местами нода быстрей, но PyPy решает эту проблему. Единственный большой плюс перед питоном — асинхронность, если сравнивать с веткой 2.x.
Ну и синтаксис после питона в ноде сильно на любителя. Авторы ведь с этим языком сравнивали тоже.
Все тесты где нода выигрывает в основном связаны с вебом и сетевым взаимодействием, что неудивительно.
Наверное, из-за того, что генераторы в ноде только на походе. А писать хочется без колбэков уже сейчас.
Ну нити вроде есть отдельными пакетами, хотя я с ними не работал, не знаю, подходят ли.
NodeJS, кажется, не очень хорошо работает на многоядерных конфигурациях. Плюс иногда очень важно знать, что данные в памяти хранятся именно так, как вы указали в программе.
Javascript с v8 работает быстро, но как то не прижился именно у нас. Меня когда я еще делал скрипты для веб страниц сильно смущало обилие коллбэков. Насколько я знаю в ноде уже есть генераторы или нечто подобное чтобы писать аля синхронно, но как то не довелось все это попробовать.
Ну и да динамическая типизация для подобного проекта думаю будет не нужна, придется писать больше тестов.
а разве промисы не решают проблему обилия коллбэков?
Они лишь уменьшают их вложенность, размазывая по коду.
Надеюсь через год-два этот язык станет ещё популярней. Жду когда появится часть нужных мне библиотек от комьюнити, пока что многие из них имеют незаконченный вид.
Мне, как питонисту, с постоянными проблемами производительности некоторых вычислений, этот язык кажется идеальным вариантом в качестве второго.
А numpy не решает проблемы вычислений?
Позвольте попридираться к формулировкам, а тот тут в каментах уже задают вопросы. Я вот про этот утверждение «region.GetRegionByLbs асинхронно ходит в серсис геобазы и Lbs». Думаю правильней сказать, что этот метод все-таки синхронный (т.е. пока он не отработает, последующий за ним код не начнет выполняться), но он неблокирующий, в том смысле, что он не блокирует поток ОС за счет использования goroutines.
Если до конца придираться, то он может и системный тред заблокировать на блокирующих syscall вызовах. Просто планировщик Go перебросит остальные Go-рутины на другой тред и приложение этого даже не узнает.
Естественно может. Но я надеюсь что приведенный метод написан хорошо и не вызывает блокиурющих методов :) Иначе другие горутины тоже могут блокировать поток, короче все будет как в обычном многопоточном приложении без горутин.
Я думаю там используется netpoller и ничего не блокируется. Если дойдут руки и Дмитрий Вьюков мне поможет, то попробую написать подробную статью про внутренности планировщика в текущей реализации.
Обязательно посмотрим, когда он зарелизится.
Да смотрели и предварительно он кажется очень интересным, мы хотим его тоже попробовать.
В статье несколько раз сравнили C++ и Go по различных параметрам. А есть понимание, сколько строк кода C++ соответствует одной строке кода на Go (или наоборот) в среднем?
Примерно одинаково, только что взял крошечное приложение, которое есть и на одном и на другом языке, на плюсах было 180 строк кода, на Go 220.
На таких размерах приложения результат на мой взгляд не репрезентативный. Нет данных по приложениям хотя бы на несколько тысяч строк?
Лишние 40 строк видимо выглядят как
if err != nil {
Расскажите, как вы тестируете go-код. Насколько я помню, в ответах после доклада на схожую тему рассказывали про testify и билд-сервер. Можете добавить подробностей: как собираете и получаете зависимости, что тестируете, используете ли эти билды при деплое?
С зависимостями решение как у всех: всё складывается в вендор директорию, подключаемую как дополнительный путь в GOPATH. Пока всё работает — ничего не обновляется. Если есть проблема или нужна функциональность в новой версии библиотеки — вручную обновляется и тщательно проверяются деградации.
На тестовые стенды деплой проходит через вагрант/openstack виртуалки у разработчиков, где в манифест заносится вся информация о билде (версии библиотек итд). На продакшен всё гораздо сложнее, несколько уровней проверки и постепенная выливка с помощью администраторов.
А GC проблем/тормозов не доставляет?
У нас пока не было проблем с GC ни в одном из приложений, по крайней мере мы их не замечали.
Кстати, в 1.5 GC собираются сделать намного более предсказуемым, чем есть сейчас. При идеальном раскладе возможно слегка просядет производительность, зато не будет внезапных stop the world.
Суровый брутальный обзор, но как-то так оно и есть, да. Продуктивности Go прибавляет с лихвой.
Скоро под андроид будем писать на Go, вот тогда повеселимся =)
Потому что это еще не стабильный язык, который меняется от версии к версии?
Facebook использует D, Yandex использует Go — будущее ближе, чем кажется?
Facebook использует Александреску. А Александреску использует то, что ему больше по душе.
Facebook, как и любая большая компания использует всё подряд, в том числе и Go github.com/facebookgo
Не уверен насчёт сравнения с Python. Я последний так и не осилил, например. Больше, чем пишешь логику, ломаешь голову над тем, как сделать это поизящнее. А с Go правильное решение, как правило, самое очевидное.
Да ну… Пример в студию, пожалуйста.
PS. Zen of Python:
There should be one-- and preferably only one --obvious way to do it.
import random
import string

ALPHABET = string.ascii_letters + string.digits

def first(number_of_letters):
    random_string = ""
    for _ in range(number_of_letters):
        letter = ALPHABET[random.randint(0, len(ALPHABET) - 1)]
        random_string += letter
    return random_string

def second(number_of_letters):
    return "".join(random.sample(ALPHABET, number_of_letters))

print first(10)
print second(10)


Всегда есть больше 1 способа :)
Правда в вашем случае first и second делают разные вещи — в частности, first может вернуть строку, в которой буквы повторяются.
Да, но нормальный один =). В этом случае чем больше символов, тем больше разница в скорости.
Сложение строк в цикле конкатенацией это плохой способ почти в любом языке, как мне кажется.
«На Go маленькие программы можно писать быстрее чем на C++, примерно так же быстро, как на Python. И ощущения от языка примерно такие же.» — это Вы, видимо, JSON не пробовали парсить. После Python или любого другого языка с динамической типизацией, все эти адовые структуры и\или приведения типов на каждый чих — это ад. Код для парсинга простейшего JSON-объекта получается раз в 10-20 больше, чем на Python. Что еще не нравится в Go? Ошибки по возврату функции. Вот это реально вредная штука. Если Вы везде пишете обработчик ошибок, то почему бы просто не сделать выбрасывание Exception'а по-умолчанию? Ну а если Вы не проверяете возвращаемые значения, то тогда Ваш код — это грязная ядерная бомба, которая взорвется в самый неподходящий момент.

В целом, если бы не мощная поддержка Гугла, Go так и остался бы мало кому известным еще_одним_языком. Лучше бы Гугл допилил D, вот где действительно шикарная замена C++.
Мне кажется если вы не поняли как писать на языке, это не значит что язык чем-то плох.
Json в Go парсятся просто великолепно, описываете структуру и вперёд. Не хотите описывать структуру? Есть библиотеки, позволяющие легко получить данные по пути /one/two[2]. В Go вы точно знаете что получили нужную структуру и данные, в python вам придётся всё проверять, в любом случае.
Ошибки в Go это просто обычные значения, хотите правильный код — обрабатывайте, не хотите — будьте внимательнее в дальнейшем.
Вы пытаетесь натянуть шкурку одного животного на другое и удивляетесь, что вместо носа клюв.
Мое личное мнение, что json в коммуникациях machine-to-machine с фиксированным протоколом это вообще вещь достаточно вредная. Если данные действительно динамические и посылается совсем что угодно, то json — хорошее решение. Но там где протокол постоянен лучше использовать нечто вроде protobuf. Json, msgpack это некая структура данных где они могут быть а могут и не быть и это нужно постоянно проверять, в то время как в protobuf и подобных это реализовано на уровне протокола и его пользователь уже имеет некоторые гарантии того, что данные представляют из себя то что он ожидает.
Go же в тех случаях где с json приходится работать на уровне протокола старается хоть как то жестко связать его в структуру, что по моему хорошо. Кроме того никто не запрещает работать в Go с json также как в javascript или python, можно также не анмаршалить его в структуру, а просто обращаться по какому-то пути к элементам json.
Кстати в стандартной библиотеке Go для этот есть gob, нативный бинарный формат сериализации Go объектов.
Gob хорошая вещь, но работает только в Go. :(
Имхо такая обработка ошибок как там неудобна и лучше бы они сделали исключения, в этом соглашусь. Я вообще не думаю что Go какой-то очень крутой язык, по моему достаточно средний даже. Совсем простые вещи там пишутся легко, но если требуется что-то более сложное, то языка на это явно не хватает. Для наших задач Go хорош и мы его любим за это, простые вещи можно разрабатывать и тестировать быстро.
Думаю Google сыграл большую роль в популяризации языка, без него ему было бы намного хуже.
Меня по началу тоже ломало отсутствие исключений в Go. Позже, поразмыслив, счел что в этом есть определенный резон…
Проблема исключений в том, что они в рамках идеологии многопоточности Go не универсальны. Они могут работать лишь в пределах одного goroutine. А учитывая, что конкурентность в Go это основная фишка, исключения оказываются бесполезны чуть менее, чем полностью…
А главное, я соглашусь с Робом Пайком, что ошибки в современной сетевой среде — это не исключения. Это обычная ситуация, которую надо явно учитывать и обрабатывать в логике программы.
А бросание исключения в надежде, что кто-то там его поймает, это довольно безответственный подход. Для таких товарищей наверняка в аду стоит отдельный котёл…
Так никто же не говорит бросать в надежде на что-то. Есть же checked exceptions, которые в обязательном порядке должны быть обработаны.
Использование исключений для управления нормальным (не исключительным) control flow — очень спорный подход. Например, такой код довольно сложно анализировать, что приводит к практической невозможности его заJIT'ить.
Смотря где и в каких ситуациях. В том же Erlang — это единственный способ не разводя кучу вложеных case-сов или монструозных конструкций прервать выполнение и вернуть результат.
Термин checked exception намекает на Java, в котором сказанное мной справедливо. Если говорить про Erlang или какой-нибудь Scala/Akka, то там используются куда более дешевые механизмы.
Welcome to raise_StopIteration_Python_World =)
В Go есть panic/recover, если что. А классические исключения провоцируют использование их для обработки основной логики, что не правильно.
Недостатком C++ для нас был явный оверкилл для наших целей, на разработку уходила уйма времени, также большой проблемой для нас было то, что плюсовый фреймворк для Кокаина не представлял никакой возможности работать асинхронно, кроме как с помощью коллбэков.

При том, насколько легко честные легковесные fiber'ы реализуются в C (для C++, возможно, понадобится чуть допилить проброс исключений) прямо «на коленке», эту фразу корректнее переписать: «Нам хотелось чего-то нового и предлогом послужило...»
Да, сделать на коленке, допилить проброс исключений, форкнуть кокаиновый фреймворк и сделать так чтобы он со всем этим работал. Очень тривиальная задача.
В Qt C++ работать асинхронно и тестить асихнронные вызовы так же приятно, ИМХО.

Я рассмотрел эту возможность здесь на примере Yandex Dictionary Api.

P.S.: это не реклама, просто тема эта мне явно близка.
В статье ни слова как это всё работает внутри Qt. Может раскроете тему?
Отличная мысль, если это востребовано.
Попробую в ближайшее время написать про это.
Работает на основе сигналов и слотов, схема похожая на работу с коллбэками, но гораздо приятнее. Лично меня асинхронный метод, который выглядит как синхронный в Go сбивает с толку.
Сигналы и слоты это просто интерфейс, вы можете их сделать хоть в php. Что там внутри, вот что интересно.
А какой версией go вы пользуетесь? Я вот что-то уже два дня имею головную боль от попытки отладить go 1.3 (или 1.3.1) с помощью gdb 7.7 (или 7.8).
Мне кажется это плохая идея, если вы не знакомы с устройством runtime'а или не являетесь разработчиком оного runtime'а… Сломаете себе мозг. Лучше используйте отладочные логи и/или TDD.
Насколько я помню, отладчик достаточно сносно работает, я правда не пробовал его в 1.3.x. Но до этого серьезных проблем не было.
Ну, в сносности я не сомневаюсь… Просто, если приложение многопоточное с кучей взаимодействия между потоками, то большую часть времени вы будете дебажить рантайм, чем свой код… Я в этом смысле.
Так я отлаживался в gdb, чтобы понять почему у меня логи не пишутся)). Не пишутся, потому что в log4go bug.

А главная проблема при отладке — это при очередном вызове gdb next, программа начинает выполняться без остановки до следующей точки останова или, если точки нет, до конца. Я вот думал, может это из-за того что в 1.3 поменялась модель роста стека и gdb начинает казаться что он в другом фрейме. Но если у остальных людей все работает, значит это просто у меня руки кривые (.

Ну и info goroutines выдает Python Exception <class 'gdb.error'> Attempt to extract a component of a value that is not a (null).
По-моему, отлаживать код на Go отладчиком — вообще не самая удачная затея.
Sign up to leave a comment.