Comments 284
Тем, кому интересна эта тема, читают специализированную литературу и практикуются без попыток увеличения ЧСВ через написание статей, чья выжимка выглядит как "смотрите чё могу посоны".
Смотрите как удобно и лаконично! Если у имени есть скобочки (), то это функция, не надо никаких function, как в Javascript, но и возвращаемый тип указывать не обязательно!вы не описали вообще ничего в рамках статьи. Причём даже то что описано — показывает вас как профессионала с не самой лучше стороны.
Возможно, вам стоило сначала как следует рассмотреть развивающиеся проекты подобного рода и получше разобраться в вопросе.
Таких, чьё мнение стОит учитывать — не найдёте.
Мне нравится ваш энтузиазм, сам таким же был в 15, но вы не описали потенциальных преимуществ своего языка (мелкие изменения в синтаксисе — ерунда, к таким деталям привыкаешь за день), ни деталей его устройства (вы хотя бы понимаете принципиальную разницу между c++ и javascript? Ну, помимо того, что один компилируется, а другой, если не повезло, интерпретируется?)
И с ходу отбросили llvm и т.п. — похоронив надежду сделать хорошую оптимизацию в своём языке.
В общем, привлечь сможете только таких же юных энтузиастов, а нужен суровый наставник :-)
Тем лучше для вас — в 40 с гаком приятнее быть молодым энтузиастом, чем старым пессимистом :-).
Тем не менее, вам сейчас нужен именно пессимист, который будет задавать неприятные вопросы (вообще говоря, основные вопросы вроде "какова цель", "в чём преимущества" и "чем за них придётся платить" должны были задать вы сами и сами дать ответы на них в статье).
Кстати, тут уже всплыла следующая проблема — библиотеки. Язык, если вы не делаете качественную оптимизацию — ерунда, думаю, тут у многих в истории болезни как минимум написание интерпретаторов. Но вы же замахнулись на переносимость. Как вы себе представляете эффективную библиотеку, единую для C и JavaScript?
Собираетесь ли вы в своём языке предоставить GC? Дать доступ к raw pointers? Поддерживать замыкания? Это всё — ключевые вопросы, меняющие структуру языка куда сильнее, чем изменения в синтаксисе, которые вы описали в статье.
Сейчас вырисовывается такой план:
1. Сделать трансляцию в Javascript
2. Сделать трансляцию в С++ и чтобы работало одинаково с Javascript
Далее я идут в яндекс/гугл/майру, беру у них несколько миллиончиков зелёненьких на разработку и дело в шляпе. Если не дадут бабки — будет просто язык, на котором буду писать только я сам, и возможно, несколько единомышленников…
Не дадут, разумеется. И единомышленников, которые помогут — вряд ли найдёте.
Сделать нечто, транслирующееся и в js, и в c++ — несложно. Только возможности будут несопоставимы ни с тем, ни с другим — просто потому, что вы унаследуете ограничения обоих.
Я не зря спрашивал про gc/указатели/замыкания. Это ключевые моменты, влияющие на внутреннее устройство языка, а не синтаксический сахар, про который вы говорили в статье.
P.S. Гомерчик прикольный!
Не надо учить людей изобретать свой велосипед для каждой задачи.
Открытые проекты для того и существуют, чтобы люди могли создавать что-то полезное, используя уже готовые и хорошо протестированные сотнями разработчиков, инструменты, чтобы никому не приходилось тратить 20 лет на создание своих инструментов с нуля для каждого проекта
Для чего нам будущее, в котором будут сотни проектов, наполненные багами и уязвимостями, написанные с нуля недо-разработчиками?
Кто захочет переписывать все библиотеки с Python для нового языка только потому, что он новый? Ни у кого на это нет времени
А гитхаб это прямой пример того, о чем я говорю:
— берем существующий проект / инструмент с исправленными багами и закрытыми уязвимостями, проект на который уже была потрачена тысяча часов работы.
— улучшаем этот инструмент, вместо того, чтобы писать свой с нуля
Если вы уверен, что он таковым является, тогда стоит описать его преимущества и принцип работы в формате так называемой white paper, чтобы профессиональные разработчики заинтересовались и помогли написать.
Если же вы не уверены, что этот язык настолько хорош, что многие разработчики бросят свои Python, C, JS и перепишут все существующие фреймворки и библиотеки ради него, тогда, для кого он будет нужен?
беру Cj лабаю на нём сайтик. На выходе html/js/css/php или nodejs.
То есть у вас в Cj еще и разметка будет?
Вы пытаетесь сделать god language. Не взлетит.
Совершенно не понятно, зачем добавлять в свой язык конструкции, чтобы генерить из него JS/TS (или другой язык), если можно просто взять JS/TS, из которого генерить все остальное.
Какой профит от собственного языка?
Видимо, хотелось сделать какой-то более чистый синтаксис.
Получилось?
Вы что предлагаете взять TypeScript и генерить из него под все платформы?
Я предлагаю взять какой-нибудь устоявшийся язык, с большим тулсетом, и генерить из него.
Вы будете участвовать в написании такой штуки?
Нет, я считаю это гиблой идеей.
C# так уже умеет, только не для целых программ, а для выражений.
Я работал как минимум с двумя библиотеками которые, фактически, умеют превращать C# в SQL и с одной которая умеет превращать C# в Javascript (и я исправлял ошибки последней — так что можно сказать что участвовал в написании, правда это было в закрытом форке).
Ну, вы в курсе про Kotlin, да? Андроид и веб есть, натив, вроде тоже. Посоны 5 лет писали до версии 1.0.
и что с ним на айосе можно делать?) Хеллоу ворлд написать?
Ок понял, значит не нужно. Когда будет полноценный UI фраемворк + интеропобилити с 3rd party тогда поговорим — а так это очередное "Смотрите, я скомпилировал свифт под андроидом!"
Kotlin/Native is primarily designed to allow compilation for platforms where virtual machines are not desirable or possible (such as iOS, embedded targets), or where a developer is willing to produce a reasonably-sized self-contained program without the need to ship an additional execution runtime.
Это я к тому, что команда разработчиков, получающих по 200.000р в месяц, полировала язык 5 лет, и всё ещё не закончила. Тут вылезаете вы с вопросом "А если хочу в айос?", в то время как у вас не компилятор, а транспилятор, который умеет 0.01% псевдо-джаваскрипта переводить в джаваскрипт 1-в-1.
А что, бишь, в вашем языке от "мощного C++"?
Кстати, если Вам интересно, предлагайте, что хотели бы увидеть?
Я предпочел бы это развидеть. Я считаю, что эта помесь ежа с ужом, как обычно, превратится в колючую проволоку.
Чтобы сделать хороший продукт, надо иметь цель помимо "сделать хороший продукт". Какие задачи преследует этот продукт? Чем он выгоднее конкурентов?
Хочу писать веб страничку — Cj генерит Javascript, хочу Android — генерит Java под Android и т.д…
- Тогда при чем тут вообще C++?
- Как вы будете решать проблему с зависимостями?
- Почему не использовать любой существующий язык?
2. Поясните подробнее, плиз?
3. Предложите, какой язык я должен использовать?
Хочу десктоп — Cj генерит, С++
Зачем вам для этого C++ в языке?
Поясните подробнее, плиз?
Вот у вас есть, значит, приложение, которое должно сохранить файл, полученный с сервера, на диск. В приложении написано что-нибудь типа stream.SaveTo(path)
. Во что это будет компилироваться на десктопе — более-менее понятно. А на остальных платформах, вот прямо с браузера начиная?
Предложите, какой язык я должен использовать?
Любой, для которого есть готовый парсер. Для ваших целей нужен не новый язык, а бэкенд, который одно и то же синтаксическое дерево компилит в разные целевые языки.
Button button;
button.onClick = () {
this.setColor(red);
}
Видимо, как-то так. Для JS и C++ будет какой-то похожий код.
Для… C++ будет какой-то похожий код.
Так его интереснее всего посмотреть!
А нулрефа в этом замечательном коде разве не будет? И где же именно будет создана кнопка, на каком скрине, в каком его месте?
Просто попишите на Haxe, на том языке, где это уже давно есть и попробуйте понять какие проблемы содержит данный подход.
Помимо этого стоит ознакомиться с историей ASP и почему он мёртв. Почему некоторые банковские сайты часто требуют IE6/7 и отказываются работать в современных браузерах (в том числе и в современных IE, как бы сюрриалистично не звучало вместе "IE" и "современность". Я уж не говорю про Edge). И почему ему на смену пришёл ASP.NET (это совершенно другая технология, не стоит путать).
Норм идея?
Мне, кстати, интересно, каким боком сюда ASP.
Это и asp.net-контролы делают сейчас. Это в любом случае была не кросс-компиляция, а просто готовая функциональность.
Затрудняюсь с ответом. У контролов есть свои сильные стороны, а вот что убило asp — я уже и не помню.
(ну, помимо выхода asp.net)
Я не ошибусь, если предположу, что эти компоненты используют лишь для совсем внутренних админок и макетов? Где надо побыстрее, а не так, чтобы оно нормально работало?
Это как раз принципиально. Если вы не понимаете, как будут решаться такие вопросы, заявленная вами цель недостижима.
Собственно, если бы я вдруг брался за такую амбициозную задачу, я бы начал как раз с того, что просто набросал, как будет выглядеть код, как исходный, так и целевой. Возможно, уже на этом этапе было бы понятно, что задача не имеет решения.
Но есть какие-то общие вещи, которые можно сделать универсально. Например, создать кнопочку.
Ага, для сервиса особенно.
Сама по себе идея разрабатывать части web-приложения на C/C++ далеко не новая — другое дело, какой результат вы хотите получить от такого подхода? Возможно, вам будет интересно ознакомиться с WASM: http://webassembly.org/docs/c-and-c++/
Команда, работающая над WebAssembly, включает разработчиков из компаний Mozilla, Google, Microsoft и Apple. Надеюсь они когда-нибудь осилят ))
Я, конечно же, знаю про эту поделка и она пока что выглядит менее жизнеспособно, чем моё решение.
Уже игры на Unity в WebAssembly есть, а вы говорите "выглядит менее жизнеспособно"
Уже есть Emscripten, который из C/C++ генерит JavaScript
Допустим. Тогда:
int a = 1;
a = a + "some";
Что в этом случае должно произойти?
Там выше был пример, что "int a" превращается в "var a". Следовательно будет:
var a = 1;
a = a + "some"; // "1some"
А это вполне валидный и рабочий JS код. По-этому никаких ошибок.
С другой стороны, почему var, а не let...?
А var или let не принципиально. Это как пример. let не поддерживается старыми браузерами, значит пусть обновляют)
На счёт «не принципиальности». Какой результат должен выдать вот этот пример на вашем языке?
int a = 23;
some() {
a = 42;
}
// Вопрос: Чему равен "a"?
Если «let a», то 23 и одна глобальная "(global || window).a" переменная, равная 42
Ну, например, в локальном скоупе создать изолированную память (сгенерировать уникальное имя переменной, например). Заблокировать к ней доступ извне (сделать вид, что её не существует). Туда добавить нужное значение. Прокинуть наверх значение с именем переменной, сделав вид, что объявление "a" действительно было. Внутри вложенных скоупов генерировать свои имена, прокидывать наверх. И так далее.
В результате получаем, что эти три строчки превращаются в 'дцать.
Например (где xxx, yyy, и т.д. — генерируемые имена):
var xxx = (function() {
var yyy = 23;
return {
a: yyy,
some: function some() {
var zzz = 42;
}
};
});
var a = xxx['a'];
var some = xxx['some'];
delete xxx;
Почти похоже на сопоставимый код, но:
1) Все аргументы надо прокидывать, как в IIFE, так и внутрь объекта (ака набора переменных контекста).
2) Тот же самый IIFE, кажется, меняет контекст this и код будет не равноценным.
Отлично, первый этап пройден. Мы выяснили откуда во всех трансляторах такая куча "лишнего" кода и почему без него не получится.
Переходим к stdlib. Начнём с чего-нибудь "простого", функции получения длины строки. Давайте попробуем написать код на нашем убер-Cj:
(Увы, хабр не поддерживает нормально utf-8, так что картинкоё)
Такая строка занимает 21 байт в utf-8. Что-то не сходится. Как мы будем считать? И давайте учитывать, что в JS длина этой строки 12 символов, хотя физически их 11. А на C++ как мы будем считать? Подключим внутрь бинарника какой-нибудь icudt (пыщ: http://site.icu-project.org/), объёмом в ~25 мегабайт?
Несомненно, отсутствующий код — самый чистый.
Вы на Visual Basic никогда не писали? "auto" наводит на мысль, что Вы не в курсе, что такое вариантный тип.
Логично было бы ввести тип Variant, и использовать аббревиатуру "var" )))
И в чем она заключается, раз понимаете?
Из википедии: Kotlin (Ко́тлин) — статически типизированный язык программирования, работающий поверх JVM и разрабатываемый компанией JetBrains. Компилируется также в JavaScriptПочему тут называют компиляцией в Javascript, а мне нельзя? ))
А вот что получается на Javascript:
function my_func1(var p) {
Это в каком JavaScript такое валидно? А то у меня получается "Uncaught SyntaxError: Unexpected token var"
Теперь нет там var. Я даже не проверил работу Javascript, спасибо за замечание.
Я правильно понимаю, что вы решили не тратить свое драгоценное время на глубокое изучение какого-либо языка, а потратить сэкономленное на написание своего собственного?
У меня такой подход, я пишу на Microsoft Visual Studio, но в итоге получается всё кроссплатформенно. Например, сайт sitev.ru работает на своём вебсервере и своёй CMS на плюсах. Они разработаны по тойже технологии. Всё что сейчас не работает, я исправлю, не дошли руки протестировать в линуксе.
Например, сайт sitev.ru работает на своём вебсервере и своёй CMS на плюсах
У вас там адъ в разметке из стилей
Microsoft Visual Studio
Т.е. ещё и .NET???
А теперь запилите компиляцию в нативный код.
Нуу, так C++ не потеснишь… Трансляторы в JS сейчас только ленивый не пишет.
Сомневаюсь, что вы найдёте единомышленников в разработке языка под вас. Но если будут интересные идеи касательно языков — пишите нам в телеграм чат: https://t.me/lang_idioms
Вы бы лучше не торопились. Постепенно прочитали бы книжку , познакомились бы с исходным кодом компиляторов крупных языков (к примеру если нравятся плюсы, то gcc, clang). Попробовали бы поконтрибьютить (исправить парочку багов, добавить функциональность...).
Сейчас же ваше творчество выглядит обычным троллингом, никакого серьёзного фидбэка от этого ожидать не стоит. И лучше вообще удалить статью, чтобы рейтинг и карму не слили ещё больше
Предлагаю автору:
1) Ознакомиться с этим докладом: https://www.youtube.com/watch?v=HE4yyPpUsy4 обещаю, будет очень интересно и познавательно.
2) Прочитать про BNF/EBNF и взяться, например за ANTLR. В результате декларация функции, включая токены и грамматику превращается примерно вот в такую схему (на псевдоязыке, похожем на ANTLR).
%skip T_WHITESPACE [\xfe\xff|\x20|\x09|\x0a|\x0d]+
%token T_WORD [_A-Za-z][_0-9A-Za-z]*
%token T_ANY .*?
Document
: Function()?
| // и переменные
Type
: "int"
| "auto"
FunctionDefinition
: Type()? (T_WORD #FunctionName)
"("
// тут должны быть аргументы
")"
"{"
// тут должно быть тело
"}"
VariableDefinition
: Type()? (
T_WORD #VariableName
) "=" (
T_ANY #VariableValue
)
FunctionInvocation
: (T_WORD #FunctionName) "("
// тут должны быть аргументы
")" (";")?
Схема проверит грамматику и построит AST.
- Потом из дерева исключаются неиспользуемые конструкции (например переменные, которые не используются).
- Затем уже можно его превращать, либо в опкоды LLVM, либо во что угодно.
Но это уже другая история...
sitev_ru а тебе посоветую:
1) Для начала спрашивать на эту тему у шарящих людей. Не бежать накатывать статьи, которые не несут почти никакой смысловой нагрузки.
1.2) Если таких людей нет под рукой, то хотя бы на тостере.
2) Статья хоть и глупая и отхватил уже за неё минусов, но не думаю что прям сейчас надо бежать и закрывать её. Оставь до завтра. Раз уж получил по макушке, то почитай хотя бы комменты, не глупые люди пишут. Получишь хоть какие-то отзывы. Подумаешь, осмыслишь, сбросишь карму (тут можно делать один резет) и попробуешь сначала, с работой над ошибками.
Я, конечно, понимаю, что такой способ реализации тоже имеет место быть, но способ проектирования дизайна языка — крайне плачевный. Просто посмотрите видюшку, что я кинул выше и поймёте почему я именно так выразился.
На ANTLR даже чище получится:
grammar Cj;
document
: ( functionDeclaration
| variableDeclaraction
/* etc. */)* EOF
;
functionDeclaration
: type? functionName=ID '(' /* arguments */ ')'
'{' /* body */ '}'
;
variableDeclaraction
: type? varName=ID '=' varValue=any
;
functionInvocation
: functionName=ID '(' /* arguments */ ')' ';'?
;
type
: 'int'
| 'auto'
;
any
: ANY+
;
WHITESPACE: [ \t\r\n]+ -> channel(HIDDEN);
INT: 'int';
AUTO: 'auto';
ID: [_A-Za-z][_A-Za-z0-9]*;
ANY: .;
Ну такое… Парсер рекурсивного спуска как-то получше выглядит.
как Cj справиться с этим.
без этого новый язык в наших реалях безсмысленно проектировать.
Он сразу проиграет котлину/расту и прочему
Автору успехов! Ну и грамотешки маленько.
Но карму в этой хабродемократии школоты попортят изрядно.
Автору успехов!Большое спасибо!
Ну что вы начинаете то сразу "зачем писать свой язык, кому он нужен?". Ну хочется человеку, пусть пишет. Я вон тоже хочу "написать" (вообще язык эм ему разрабатывают спецификацию, а пишут тулчеин для него, но не суть. Это как "написать математику") свой язык, потом свою книгу и все такое, только erlang уже изобрели, а жаль.
Направим на путь истинный конструктивными вопросами. Пойдем по спецификации (боже, там текста на одну страницу, а уже куча косяков):
Идентификатор ... но не может начинаться с цифры.
Отличный вопрос появился для собеседования: а почему так сделано?
По поводу спецификации — а длина идентификатора чем-то ограничена или может быть произвольной? А регистрозависимость? Взяли бы просто абзац со спецификации C++ и все. Еще было бы неплохо список зарезервированных слов сюда включить.
void — специальный тип для пустых значений
bool — булевый (логический) тип данных
целочисленные типы: знаковые byte (1 байт), short (2 байт), int (4 байт), long (8 байт) и соответствующие им беззнаковые ubyte, ushort, uint, ulong
числа с плавающей точкой: float, double, real
char - символьный (знаковый) тип данных.
Чем double от real отличается? Как вы в js, например, беззнаковые числа реализуете (понятно что через number, я имею ввиду, например, попытку присвоить отрицательное значение в рантайме. К слову, относительно всех остальных типов — как реализуете переполнение? Если я объявлю ubyte i = 255; потом ++i что произойдет? Должно стать 0 или хотя бы бросить исключение, или что там у вас для этого будет. Прерывание! Во, крутая идея, сделайте вместо исключений единственный язык, работающий на прерываниях)? Где null потеряли? И вообще указатели. В js есть и null и undefined, вы оба их сделаете void? 2 байтА, а не 2 байт. Функциональный тип есть? Без него трудненько. А строки? А, окей, типа во второй редакции с массивами появятся и строки как массив char, так?
Для использование переменной в программе нужно просто указать её имя.
Идентификатор.
- Функция
Эм. Функции — это тип или не очень? А что касается области видимости внутри (и во вне) функции? А можно объявлять одну функцию в другой? А необязательные параметры? Вообще, они все обязательные или как?
Операции
Данная версия Cj поддерживает ограниченный набор операций
Ух! Погнали. В js (во что вы собрались компилировать) если написать 6 / 4 закономерно получишь 1.5. Во что скомпилируется конструкция
int x;
int y;
x = 6;
y = 4;
return x / y;
Результат должен быть 1. Удачи.
P.S. Зачем я все это пишу вообще? Я буду удивлен, если выйдет хотя бы версия 0.2. А текущая версия даже на версию не годится, это как-то все само подразумевается, а вы умудрились в совсем уж очевидных вещах накосячить и сделать свой язык принципиально не соответствующий поставленной цели:
Меня всегда интересовали различные направления и веб я хочу сбацать и мобайл и десктоп и что-нибудь серверное готов написать, ещё мне интересены ИИ, игры, роботы, криптовалюты… И при этом, хотелось бы всё это писать на одном языке).
Меня всегда интересовали различные направления и веб я хочу сбацать и мобайл и десктоп и что-нибудь серверное готов написать, ещё мне интересены ИИ, игры, роботы, криптовалюты… И при этом, хотелось бы всё это писать на одном языке).
Невероятно, но я прям сейчас могу на js писать под все перечисленные направления. И на практически любом другом языке, вопрос лишь в количестве инструментов и библиотек для этого. Исключение — системные языки программирования, так нужна определенная специфика. Впрочем, на js вон под микроконтроллер можно писать и ничего, как-то работает.
Обычно, вначале пишутся спецификации языка, вроде таких: https://www.ecma-international.org/ecma-262/8.0/index.html, а потом реализуется язык. Единственным исключением, на моей памяти, у которого спецификация появилась после реализации — был PHP.
Чем double от real отличается? Ещё не знаю
А зачем тогда?
потом 0.3 и т.д., ну как обычно…
Конечно пусть, только писать про это хабрапосты совсем не обязательно :) У меня тоже есть маленький самопальный язык с самопальной компиляцией (трансляцией?) в самопальный байткод с его самопальной интерпретацией, и всё это трудится на моём маленьком продакшене как простенькая числодробилка-песочница, но бежать писать посты про это я не собираюсь, там всё равно ничего интересного или уникального)
Конечно пусть, только писать про это хабрапосты совсем не обязательно :)
Надо обязательно писать такие посты, я не хочу, чтобы осталось, как у вас: где-то крутится у меня и всё! Наоборот, мне очень интересна стала эта тема и я хочу её развивать! В процессе обсуждения рождаются идеи, я читая комментарии тоже чему-то учусь, думаю, рассуждаю. Я обязательно где-то не прав, где-то ошибаюсь. Нельзя вариться в своём болоте. Хочу хотя бы доделать какой-то законченный вариант это поделки.
Вам вроде уже советовали почитать книгу драконов, да и в целом подтянуть теоретический минимум. Пересмотреть кучу спецификаций других языков, разобраться почему используются те или иные решения. Наверное, есть единственный язык на моей памяти, который стал популярный, но разрабатывался с одной лишь мыслью "в ж*** скобочки, будем табуляцией делать", и то его популярности способствовало много факторов, который нет у вашего языка на данный момент.
Идея писать системный код так же легко как на js — хороша. Да, компилируемый js-подобный язык, здорово. Я прям заинтригован. Даже слушаю внимательно, а то rust что-то не заходит, а вот C++, только с прототипами, утиной типизацией и синтаксисом js (ts) ммм [/sarcasm]. И я у вас не видел даже намека и планов на работу с памятью, а было бы интересно почитать, а без этого системное программирование не очень.
А пока что у вас получается только переизобрести typescript, только который ничего не умеет.
В общем — ссылку на компилятор в байт-код (или транслятор в C/C++, если так хочется), тогда поговорим. Либо сформулируйте цель языка иначе. Например "не нравится в какую сторону развивается typescript, нельзя писать public get и private set на одно поле одновременно, тупо же".
Задача сложная. Можно бесконечно рассуждать как лучше сделать. Я примерно вижу направление, сделал в этом направлении первый шажок. Теперь осматриваюсь, что дальше, куда дальше двигаться… Можно сесть, всё проанализировать, проработать на начальном этапе. Но боюсь после этого мне не захочется ничего делать, поняв сложность задуманного. Поэтому действую по интуиции, двигаюсь, в правильном, как я думаю, направлении и решаю проблемы по мере поступления.
Идея писать системный код так же легко как на js — хороша. Да, компилируемый js-подобный язык, здорово. Я прям заинтригован.. Давайте с вами развивать эту тему? Поясните, как Вы это себе представляете.
Разработка нового языка программирования — задача крайне сложная. В нынешнее время лезть в это направление без PhD в Computer Science от университета уровня MTI практически бесполезно. Лезть в это дело без отличной команды разработчиков-инженеров, коллег из области Computer Science и серьезного бюджета — 99.999% гарантия потраченного времени. Те, кто написали хоть сколько-нибудь популярные языки, имели уже большой опыт и бэкграуд. Например, TypeScript, на который похож тот язык, что разрабатываете вы, сделал Андерс Хейлсберг из Microsoft, создавший перед этим Turbo Pascal, Delphi, C#, J++ и участвующий в разработке MFC. Язык D изобрел Александреску — идол шаблонной магии в мире C++, имеет огромный бэкграуд в этом языке и знал, зачем нужен D (ну и поддержка Facebook, конечно). Новый модный Rust пишут уже 11 лет с поддержкой Mozilla Research, используя бэкэндом LLVM (от которого вы очень лихо отказались).
Судя по вашему подходу к разработке (тотальное нежелание разбираться в инструментах, которые призваны упрощать разработку новый языков; нежелание оформить proposal зачем это все вообще нужно и т.д.), лично я делаю вывод, что это исключительное велосипедирования ради велосипедирвания. Без четкого объяснение, какие проблемы должен решить новый язык, ни пользователей, ни разработчиков вы не получите. Если это трансляция из чего-то в чего-то, то этого уже навалом (Emscripten и т.д.).
В общем, я, также, как и многие здесь, предлагаю от этой затеи отказаться и лучше отлично разобраться в каком-то языке. Иначе это просто время, потраченное впустую.
Судя по вашему подходу к разработке (тотальное нежелание разбираться в инструментах, которые призваны упрощать разработку новый языков
Зачем мне изучать чужое, если я написал своё и оно уже работает?
нежелание оформить proposal зачем это все вообще нужно и т.д
Я потратил несколько часов на ответы на комментарии, если это не прояснило ситуацию, ну извините…
Зачем мне изучать чужое, если я написал своё и оно уже работает?
Разве работает? Последний раз когда смотрели, ничего толком не работало.
youtu.be/zwUhDOVifdw
Вам рассказать, как такое сделать на string.Replace
? Вот когда у вас будет хотя бы минимальный работающий код на выходе (т.е., тот, который можно запустить и увидеть результат), и хотя бы для двух языков — тогда и поговорим. Начните с банального вывода в консоль.
1. Добавлю операторы условия и цикла (а то уж совсем)
2. Добавлю возможность подключать внешние функции, типа вывод в консоль
3. Делаю и для js и для с++
Ну и тогда опять сюда, получать очередную порцию полезной критики))
Зачем мне изучать чужое, если я написал своё и оно уже работает?
Без комментариев.
Ну на мои вопросы вы так и не ответили. Покажите во что превратится следующий код:
int x = 6;
int y = 4;
int z = x / y;
print(z);
В z обязана лежать единица, такая уж она целочисленная арифметика, с этим ничего не поделаешь. В недоверсии 0.1 вы написали эм ничего. Абсолютно ничего, вы не поддерживаете свой же синтаксис, да и не представляете [вероятно, но есть основания так пологать] как это реализовать. Знаете, на этом этапе рано еще о компиляторе говорить, хотя бы рантайм на js опишите.
Напишите хотя бы (желательно до завтра, а то я тут немного улетаю, а уж очень хочется посмотреть) даже не компилятор, а просто рантайм, в котором мой пример будет корректно работать. Ну и добавьте на скорую руку глобальную функцию print(), который будет превращаться в console.log на js.
Хотя бы словами в комментариях на хабре, хорошо, без кода. Вперед, я жду. Думаю, тут всем будет интересно.
Ну и да, главный вопрос — что вы хотите от своего языка, какая его ниша? Я так и не понял. Универсальный язык, который умеет и в веб, и в системное программирование? Правильно?
Код функции malloc на вашем языке и чем оно станет при компиляции в js и в C в студию.
В z обязана лежать единица… да и не представляете как это реализовать
x = 6;
y = 4;
z = Math.floor(x / y);
и добавьте на скорую руку глобальную функцию print(), который будет превращаться в console.log на js.
У меня есть, конечно же, мысли, как это сделать, но пока не уверен на 100% (выкладывать пока не буду — обжёгся), как лучше… Выслушаю вашу точку зрения
Ну и да, главный вопрос — что вы хотите от своего языка, какая его ниша?
веб, мобайл, десктоп, сервер, да и всё остальное… яж хочу писать различного типа задачи на одном языке)))
Код функции malloc на вашем языке
Пока такой функции не будет. Что дальше, я не знаю. В 2017 году вроде можно обойтись без неё. Если нужно, будет обходной вариант. Язык же предполагается невероятно гибким! ))
int x = -6;
int y = 4;
int z = x / y;
Вместо каждой операции деления будете подставлять код с ветвлением? Ну ок.
Задачка посложнее
float x = 1.0 / 3.0;
double y = 1.0 / 3.0;
double z = y - x;
Ответ: -0.000000009934107
#include<stdio.h>
int main() {
float x= 1.0f / 3.0f;
double y = 1.0 / 3.0;
double z = y - x;
printf("%.15f", z);
}
Вместо каждой операции деления будете подставлять код с ветвлением?
Совершенно не так. Если присваиваю переменную, а она в Cj целая, то тогда подставляю Math.floor().
x = 1.0 / 3.0;
y = 1.0 / 3.0;
z = y - x;
console.log(z);
Вот такой код получится на Javascript. Результат = 0, отличается от -0.000000009934107. Казалось бы это уже проблема. Но согласитесь, и наш мир не совершенен. Но в концепции языка Cj, как ни странно, это нормально. Я не собираюсь на Javascript заниматься точными математическими расчётами. Хотя, на такой случай, возможно, есть какие-то библиотеки на Javascript. Плюсы языка, если вдуматься, намного перевешивают такие минусы.
Предлагаю назвать это парадоксом kahi4.
Спасибо за такую честь, но пожалуй не стоит объяснять криворукость парадоксами.
Math.floor не подойдет, потому что при отрицательных числах должен быть Math.ceil, ну и я молчу про то, что тогда может оказаться большой (и критичной, если идет речь про расчеты индекса в массиве) накапливающаяся ошибка в рассчетах, длинее чем 1 оператор. ( 6 / 4 ) * 200 например.
Про float — спасибо, в топку язык, код на котором ведет не консиснтентно. А так хорошо звучало, хотите язык для написания криптовалют, там неплохо было бы работать под видеокартой, GPGPU на языке, близком по стилю к js — здорово же, да еще с возможностью отладить это прямо в браузере.
Хотя, на такой случай, возможно, есть какие-то библиотеки на Javascript.
Ради простого умножения двух float друг на друга тянуть библиотеку на js?
В общем вам тут хотят помочь понять почему нужно делать так или иначе, а вы еще не придумав операций сравнения умудряетесь всунуть в язык костыли, причем не имея под этим никакой необъодимости а просто потому что.
Ваши загадки на JS, кстати, решаются следующим образом (спасибо спецификации asm.js):
const x = -6;
const y = 4;
const z = x / y | 0; // -1
const F = Math.fround;
const x = F(F(1.0) / F(3.0));
const y = 1.0 / 3.0;
const z = y - x; // -9.934107481068821e-9
А вот задор автора энтой поделки заставляет вспомнить про эффект Даннинга-Крюгера — вопиющая некомпетентность не позволяет ему осознать очевидные проблемы.
По-первому примеру думал так сделать: var z = x / y ^ 0;
За 2-ой пример, конечно, спасибо… Сильно!
На самом деле, эти тонкости на текущем этапе безразличны. Но на будущее, конечно, большое спасибо! Очень интересно!
вопиющая некомпетентность не позволяет ему осознать очевидные проблемыЕщё раз повторюсь, что на javascript не специализируюсь. Эти очевидные проблемы на 1-ом этапе на мою задачу никак не повлияют
Первое — тоже самое, что просто использовать ParseInt.
Про асм не подумал, верно подметили. Правда safari не поддерживает его, как и ie11.
Такс, продолжим загадки на js. Знаете, мы тут сейчас челендж устроим в комментариях.
byte x = 127;
byte y = x + 10;
// y = -119
const x = 121;
const y = 10;
const z = (zt = x + y, zt > 127 ? zt - 256 : zt);
Кто короче?
Хм, я.
const z = Int8Array.of(x + y)[0];
Боюсь, что короче, чем Int8Array.of
, уже не сделаешь, давайте следующую загадку.
const z = (x+y+384)%256-128
Циклический сдвиг в обе стороны в студию. (Да да, в C++ это тоже через либу делается).
А вообще спецификация языка Cj не так уж и обширна, а js не такой уж и бедный в плане мат. операций язык, чтобы особо чего-то напридумывать.
Может, я неправильно понял задачу, или плюсы отличаются от ansi C в плане битовых сдвигов?
function rot32(x, s) {
s %= 32;
return (x>>>32-s|x<<s)>>>0;
}
const x = 0b11000100101000111001110010110010;
console.log(
rot32(x, 10) === 0b10001110011100101100101100010010,
rot32(x, -10) === 0b00101100101100010010100011100111,
)
#include <stdio.h>
#include <stdlib.h>
uint32_t rot32(uint32_t x, short s) {
s %= 32;
return ((x>>(32-s))|(x<<s));
}
int main(int argc, char *argv[]) {
assert(rot32(0b11000100101000111001110010110010U, 10)
== 0b10001110011100101100101100010010U);
assert(rot32(0b11000100101000111001110010110010U, -10)
== 0b00101100101100010010100011100111U)
}
Для uint64 сделать можно, но очень неэффективно из-за ограничения в 53 бита на мантиссу в js.
Про плюсы я имел ввиду что нет отдельного оператора под это, но задачу вы поняли верно!
Хм, из серии "олимпиадного программирования", на практике еще реже нужно, чтобы работало именно так, но ради интереса задачка: сделайте так, чтобы rot32(1, -1)
вернуло отрицательное число, а не 2147483648. Только без использования typed arrays.
Да и вообще, функцию parseInt32, чувствительную к знаковому биту, в студию.
Мой вариант (позволю себе как раз забрать вариант с typed array)
function parseInt32(binary) {
return Int32Array.of(parseInt(binary, 2))[0];
}
parseInt32('10000000000000000000000000000001')
//> -2147483647
Ладно, у нас тут не олимпиада, пора заканчивать. Хотя идея набрать подобных задачек на пятничную статью мне понравилась.
function parseInt32(value) {
return parseInt(value, 2) | 0;
}
parseInt32('10000000000000000000000000000001')
//> -2147483647
Собственно, SerafimArts выше написал кратчайший возможный вариант — x|0
, эквивалентный касту в int32. Поэтому rot32(1, -1)|0 === -2147483648
.
Хм. Теперь мне стыдно, что не знал, за весь свой опыт использования js ни разу на это не напирался, что даже сразу не вспомнил о такой особенности.
"42.5" | 0 // 42
Строки выходят за спецификацию asm.js, поэтому работать будет, но еле дыша, т.к. не пройдет валидацию.
Жду реализацию деструктора на js.)
Вот это как раз самое простое: в js деструктор — это обычный метод со специальным именем, который можно вызвать для освобождения ресурсов.
А теперь тоже самое для статичных (выделяемых в стеке) фукнций. Хотя впрочем там тоже самое, только компилятор расставит. Ладно, вопрос снимается, но компилятор (который на самом деле транслятор), который будет все это поддерживать, все еще ждем. (И да, почему тогда бы просто не взять C++ и не транслировать его в асм?)
А теперь тоже самое для статичных (выделяемых в стеке) фукнций.
Имеются в виду функции, использующие переменные из activation object, то бишь замыкания? Они такие же объекты с похожим жизненным циклом, так что отлавливать и подсчитывать ссылки на объекты из activation object проблем нет.
Еще раз — потенцаильная сложность это функции из host object, типа DOM-модели, но это тоже обходится в transpile-фазе
но компилятор… все еще ждем
Это вопрос к автору статьи, к которому я никакого отношения не имею. Это лишь ответ на вопрос о том, что при должной сноровке поддерживать деструкторы в ES262 не представляется проблемой
Имеется ввиду, что в C++ можно написать так:
int main() {
SomeClass objectName();
}
(С точностью до синтаксиса), дестркутор при выходе из функции вызовется автоматически. Но да, никаких сложностей тут нет, я что-то надумал уже себе, у нас тут резкая смена погоды, соображаю сегодня не очень
Забавно, что приведенный Вами код с точностью до синтаксиса вообще не создает объект, а декларирует прототип функции в лексическом scope (См. https://en.wikipedia.org/wiki/Most_vexing_parse#Example_with_classes или вживую тут https://ideone.com/J3Y0oN )
Но в целом понятно, что Вы имели в вид
На платформе node.js решается очень легко — https://www.npmjs.com/package/weak и подобное
Для клиентской стороны немного сложнее, потребуется babel-плагин, осуществляющий обертку объектных сущностей — вроде таких https://www.npmjs.com/package/babel-plugin-source-wrapper или https://gist.github.com/IhostVlad/9310188edbdbc9f62dc3107417cc8fe4
Основная сложность в том, что придется обернуть взаимодействие с native и host-object-функциями, которые также могут хранить внутри себя ссылку на объекты — да, это объемная работа, но вполне реализуемая.
К тому же, большинство обертки и преобразования для DOM-модели уже решено здесь: https://github.com/DevExpress/testcafe-hammerhead/tree/master/src/processing
т.е. еще раз написать emscripten, верно? :)
А вообще я уже вижу рантайм этого языка:
- при запуске выделяется UInt8Array размера под статические переменные, а каждая переменная транслируется в структуру:
{ name, type, pointer }
Маллок просто расширяет этот массив на заданное количество байт, а так же возвращает указатель. Мемфри — ну понятно, по аналогии. Можно даже реализовать unsafe code и дать прямой доступ к указателям! Код с прямым доступом к указателям, который компилируется в байткод под виртуалную машину на js! Не круто ли? Не этого ли мы хотели?
В 2017 году вроде можно обойтись без неё.
Хоть в 2050 году эта функция будет нужна. Хорошо, можно обойтись без нее, тогда приведите модель работы с памятью вашего языка. Например, где вообще создаются переменные? В куче? В стеке? Как получится? А динамически выделяемая память? Ах да, вы язык разрабатываете, вам не до таких мелочей, когда понадобится, тогда и подумаем. Хорошо самолеты делают не так, а то шасси бы разрабатывали когда самолет уже в воздухе и пора садиться.
Если вы не собираетесь использовать этот язык как системный, то никаких преимуществ перед js, Kotlin, Python, PHP, C#, Java, [любой другой язык прикладного уровня] вы не показали, а синтаксис пока что вы предлагаете несостоятельный. (А если собираетесь, то еще и перед Rust, D, да даже плюсы). В чем тогда идея?
Хоть в 2050 году эта функция будет нужна.
В Javascript не нужна, да и в С++ от неё отказались
Хорошо, можно обойтись без нее, тогда приведите модель работы с памятью вашего языка. Например, где вообще создаются переменные? В куче? В стеке? Как получится? А динамически выделяемая память?
Пока предполагаются только динамические массивы: sitev.ru/post/174
Ах да, вы язык разрабатываете, вам не до таких мелочей, когда понадобится, тогда и подумаем. Хорошо самолеты делают не так, а то шасси бы разрабатывали когда самолет уже в воздухе и пора садиться.Совершенно верно, это не самолёт, это программа. В этой задаче я не работаю на дяденьку, а пишут в своё удовольствие. Если нет полного описания, значит я так решил или пока не продумал до мелочей как будет и это правильно!
Если вы не собираетесь использовать этот язык как системныйКонечно, собираюсь!
то никаких преимуществ перед js, Kotlin, Python, PHP, C#, Java, [любой другой язык прикладного уровня] вы не показали, а синтаксис пока что вы предлагаете несостоятельный. (А если собираетесь, то еще и перед Rust, D, да даже плюсы).Синтаксис более минималистический, более чистый. Преимущества есть, но очевидны, если понять идею того, что я делаю.
В чем тогда идея?Вроде распинался несколько часов, или уже даже дней, отвечал на комментарии, а вы всё не смогли понять идею. Странно. Идея такая: пишу на Cj и генерирую в Javascript или С++ или любой другой язык и поэтому я могу выполнить любую задачу заказчика на одном и том же языке программирования!
Теперь понятна идея? Разве это не круто? ))
У вас "более чистый синтаксис" только потому, что вы ничего не поддерживаете.
Чтобы выполнить "любую задачу", языка недостаточно.
О, динамические массивы!
identifier [ ] ;
… а какого он типа-то? Можно сделать так?
array[];
ar[0] = 5;
ar[1] = "str";
Как определяется длина массива?
array[];
array[0] = 1; //так, наверное, можно
array[1] = 2; //так, наверное, тоже
array[3] = 4; //а так?
x = array[2]; //чему равен x?
x = array[4]; //а теперь?
Тип можно задать так:
int a[];
Как определяется длина массива?
array[];
array[0] = 1; //так, наверное, можно
array[1] = 2; //так, наверное, тоже
array[3] = 4; //а так?
x = array[2]; //чему равен x?
x = array[4]; //а теперь?
Интересные замечания. А ещё спрашивают, зачем я на Хабр обратился
Эти замечания очевидны любому, кто хоть сколько-то писал на разумных языках. Если вам они не очевидны, вам надо не на Хабр, а в учебник.
Тип можно задать так:
А если не задать, то что будет?
Как определяется длина массива?
Так что с длиной-то?
Вы знаете что такое язык программирования системного уровня?
У вас есть только микроконтроллер, нет никакой ОС, любезно предоставляющей вам функцию выделения памяти.
Я пишу
a[];
a[999] = 123;
Чем оно станет после компиляции под микроконтроллер/GPGPU? Кто будет резервировать память?
В C++ от того, что функция malloc ушла внутрь new, она никуда не делась и вы можете по-прежнему определить ее руками.
Отсюда либо откажитесь от слов "системное программирование" и "вся мощь C++", либо вменяемо распишите модель памяти и работу с ней. Иначе не бывает, C++ без прямой работы с памятью никому не нужен.
Идея такая: пишу на Cj и генерирую в Javascript или С++ или любой другой язык и поэтому я могу выполнить любую задачу заказчика на одном и том же языке программирования!
Я бы мог вас отправить читать теорию, почему так не получится сделать для языков, работающих на столь разном уровне, но пытаюсь вам объяснить на пальцах. Язык, который одновременно транслируется и в C++ и в js будет хуже их обоих. Единственный вариант — создавать свой рантайм, но а: уже есть java/c#, б: вот только на js еще и рантайма не хватало. "Мы запустили интерпретатор внутри интерпретатора, чтобы вы могли интерпретировать, пока интерпретируете". Как и на C++, к слову. Да и вообще, зачем вы паритесь?
Вот вам отличная идея, как ответить на все мои вопросы: напишите транслятор в js, а чтобы поддерживать C++ — просто поднимайте внутри C++ движок js. И в java так компилировать можно. И в шарп. Oh wait...
Автор либо тролль, либо у него что-то не в порядке с головой, либо просто недалекий.
Там есть маленькая виртуальная машина, статические скоупы, динамическая строгая типизация, лямбды, замыкания, оптимизация хвостовой рекурсии, примитивный remote repl… И, да, там тоже свой лексер и парсер. И даже мотивация была — DSL-движок, для описания всяких игровых моделей.
Вот только я довольно хорошо осознаю «серьезность» проекта, не тащу его на хабр, и в пет-проджекте использую банальный Lua, а на работе — проприетарный скриптовый язык с 20-летней историей.
Зачем вы принесли вот это на хабр и что у вас на самом деле есть?
Зачем вы принесли вот это на хабр
Как я понимаю, Хабр — это площадка для ИТ-специалистов, где человек выкладывает статью на какую-то интересующую тему его и сообщество обсуждает это.
Куча статей просто не о чём, хотя на такие же темы:
habrahabr.ru/post/236907
habrahabr.ru/post/274083
и т.д…
Моя статья даже поинтереснее будет, как мне казалось. Но видимо ошибался.
Человек разрабытывает транслятор/компилятор. Сложная тема, интересно услышать мнение специалистов. Я не специализируюсь на разработке компилятора, интересно услышать спецов, в принципе, и я услышал…
А это что за комменты?
Автор либо тролль, либо у него что-то не в порядке с головой, либо просто недалекий.такие оскорбления запрещены правилами Хабра. И где модератор? Нету )
Там есть маленькая виртуальная машина, статические скоупы, динамическая строгая типизация, лямбды, замыкания, оптимизация хвостовой рекурсии, примитивный remote repl… И, да, там тоже свой лексер и парсер. И даже мотивация была — DSL-движок, для описания всяких игровых моделей.
У вас всё сложно, поэтому и осознали сложность, а у меня всё намного проще и реально реализуемо, хотя есть и большие минусы, мне их указали комментаторы, но я о них даже не задумываюсь, потому что плюсов в моей идее намного больше!
у меня всё намного проще
… потому что ничего не делает, ага.
Вот только до реального применения все это еще пилить и пилить.
А чем чёрт не шутит, я вот пишу язык с лисп-подобным синтаксисом (но совсем не лисп-подобной структурой данных) для применения в качестве кода, которым нестандартные данные могут быть представлены в JSON. Пожалуй, моя поделка заслуживает ещё меньшего внимания, чем Ваша, однако область применения есть (собственно, от неё и плясал).
Не хотите ли рассказать о своей идее по подробней?
Пока не хочу. Слишком оно сырое.
Идея не может быть сырой. Просто у меня похожие идеи. Могли бы заняться перекрёсным опылением.
Идею тоже нужно хорошо сформулировать, прежде чем излагать...
Ну, если сформулируете — присоединяйтесь: https://t.me/lang_idioms :-)
www.youtube.com/watch?v=T-BZvBWiamU
Cj — новый язык программирования