arturo-lang / arturo

Simple, expressive & portable programming language for efficient scripting
http://arturo-lang.io
MIT License
695 stars 31 forks source link

Benefits/features and vision #44

Closed Martinsos closed 3 years ago

Martinsos commented 3 years ago

Hi @drkameleon , impressive project :)! I like how simple Arturo is, and on the other hand I know how much work it takes to implement a project like this, very cool.

I like documentation, it is pretty clear and to the point (I liked ASCII art of interpreter architecture :D!).

While I am guessing this project is in big part for your own satisfaction and learning, I do presume it is also intended for real usage by others potentially, in production? If so, it might be attractive to dedicate a part of documentation to explaining why would somebody want to use Arturo. Maybe list a few benefits -> maybe that it is very easy to learn, or that it is readable, compare it to other languages. I understand that it is still in early phase compared to other languages out there so it might be hard to have solid claims of why is it better than another language, but this is where vision comes in, as additional part of documentation -> you can explain where do you want Arturo to be and how do you want to make it different / better / special. This then also serves as guidance for future design, not just for you but for others who want to contribute and join you in building Arturo. And it also helps people place Arturo -> what should I use it for, what is it good for? Although I am guessing you are also still figuring out the use cases?

Anyway, very cool, I am looking forward to future developments!

github-actions[bot] commented 3 years ago

Thank you for submitting an issue! :)

drkameleon commented 3 years ago

@Martinsos Hi!

First of all, thanks for your kind words - really appreciated.

You have some good points here.

I started Arturo around a year ago, although brainstorming on the project started much earlier - not to mention that the "language design bug" had beated me years and years ago, probably since I wrote my first line of code, back in 1994 [no, I'm not that... ancient (lol), although I was fortunate enough to start coding when I was roughly 7 years old...]

Now, of course, designing and implementing a language is an absolute fun and pleasure in itself - I won't deny that. And as the saying goes, I would do it even if it served no purpose whatsoever.

However, as you very well mentioned, each language should have a target audience, and preferably a well-defined one (and given that you mentioned, I most definitely will ;-) ). Of course, things at times take shape as a project progresses... But if you want me to list what I had (and still have) in mind when I first started out, here's the brief idea:

Now... by all this that I have written, I guess you'll know by now why I am also interested in Wasp. The main idea is very interesting, plus... I am very very fond of the implementation language you've chosen. If I had to pick one language for its elegance, that would be Haskell (not that I would consider myself... fluent, by absolutely any means, despite having ... Learned myself a Haskell for a great good (lol) and tried my hand at it by solving some 30-40 Project Euler exercises). But I still appreciate its beauty.

Btw, given that your project is still of a... manageable size (for now), perhaps it would be a good idea to study your code a bit more and see if I can find my way around - it would be a great idea both to contribute somehow and improve my Haskell skills :).

(For Arturo, I finally - after 10 different approaches, C, C++, D, etc - decided to go with Nim, simply because I wanted something (a) as fast as C, (b) a bit more user-friendly than C, (c) mature - and Nim ticks all the boxes)


Regarding this:

Btw. I have been having some fun with following "Crafting interpreters" book and implementing their Lox language in Haskell, that was a lot of fun! Do you have any resources to recommend, for learning to write programming languages, what worked well for you?

I agree that Crafting Interpreters is a very interesting book. Terence Parr's (the ANTLR guy) "Language Implementation Patterns" is also one I would recommend - albeit a tiny bit too... Java-oriented.

I could also mention the famous... Dragon Book - although it's definitely not an easy read, nor for everyone, and might be an overkill in most cases.

Now, if you want to know what I think... go for source code. I myself am a very practical show-me-the-code type of programmer. So, get your hands on EVERY language implementation you're interested in, in ANY possible language, and study it. (I have a folder full of tens and tens of subfolders, each one with some different compiler/interpreter). It can't get more useful than that ;-)

Just my .2 cents!

Cheers from the south of Spain by a crazy Greek developer!

P.S. I've been to Croatia, loved it of course and the balkans in general ;-)

Martinsos commented 3 years ago

Thanks for the great answer, it is great discussing this stuff with somebody so passionate as you obviously are :D!

It is cool to hear that you have an idea for use cases where Arturo would be used, now I have a much better picture of why you designed it the way you did, and of course what you are going for.

I read the README, looked at some code examples and read the Library reference, and while I certainly don't understand a lot of stuff yet, I do feel I got the basic idea! Nicely written docs btw., I like the writing style, it is both fun and to the point :). Main question that remains after reading all that, at least for me, was how do all these features work together, how does it feel to write something bigger in Arturo and how it compares to other languages. Or one way to put it is: ok these are features, but what are the benefits? Why is it cool that it has these features? I guess I should check the examples and try to write something bigger myself :), but I didn't get there yet! But on the other hand I am sure there will be more people like me who don't have time and might forget to revisit it later, so that is why I am mentioning this -> it would be great to offer them that information in shape that is easy to consume, so they get interested.

For example, the idea of it being "mother of all DSLs" sounds very interesting, but I am not sure why is that so, what makes it very good for that purpose? This is probably due to my lack of experience with DSLs (although I am writing one :D!) and no knowledge of Rebol paradigm hm.

I feel now like I am babbling a little bit, but to sum it up, I would suggest putting benefits / vision in structured manner in the documentation, to make it easier for people to get involved into the project (and excited about it). That said, it might be that people who will be most interested in using it for DSLs don't need that kind of explanations, and it is just that I am not a target audience.

Replacing Electron and Flutter - wow those are ambitious goals, but you seem to be well on your way towards it, I am excited to see how will that evolve :)! 100 languages -> I agree, this is in big part reason why we started doing Wasp -> web dev is suffering a lot from having to use a ton of different technologies to build even smth very simple. Although, I do think there is also some sense in using DSLs for specific purpose (well of course it does, it is in their name :D!), and actually web dev is actually a pretty complex thing in its essence -> GUI, multi user system, network delay, possible sudden need for scaling resources, ... -> it makes sense to have DLSs for specific parts of it. The problem is in how well are those DSLs integrated with each other, how easy is it to use them together, and how much time do we need to spend to get them working seamlessly with each other. And certainly one solution to that is to have them be embedded DSLs - really just libraries in a single language.

Contributing to Wasp -> well that is awesome, you would be our first contributor :D!! If you want to learn some Haskell, it could be a good opportunity: as you said, project is still relatively small, and another thing is that we are not Haskell masters, so we mostly use relatively simple features ("Boring Haskell"), it shouldn't be hard to grasp the code and add to it (we even have "good first issue" issues :D!).

Haskell -> Well, to be honest, big part of why we chose is because we have been playing with it for some time and it was really fun, and we wanted to learn it better and do a real project in it. And we used an excuse that Haskell is good for writing compilers to convince ourselves it is a good move :D. We learned on the way also some bad sides of Haskell, and it has certainly been harder to learn it than most other languages, but on the other hand it does often feel great to get stuff done in it :). Oh and I saw your PRs, very exciting, we will respond to them as soon as we can, thanks a lot :)!

Nim -> I keep hearing about Nim lately, now I am thinking I should probably take some time to learn more about it! Sounds like a good choice from what you explained and from what I just read.

Thanks for the book recommendations, I just ordered the one from the ANTLR guy, it seems to have right ratio of theory/practice for my lvl of knowledge :).

Ha it is great to hear that you liked Croatia, I have also been to Greece just a couple years ago and it was very fun, I learned how much I love greek salad (yum feta cheese) and now I eat it very often -> healthy, tasty and quick to make so you can spend that extra time on programming :D!

drkameleon commented 3 years ago

@Martinsos Good morning!

I read the README, looked at some code examples and read the Library reference, and while I certainly don't understand a lot of stuff yet, I do feel I got the basic idea! Nicely written docs btw., I like the writing style, it is both fun and to the point :).

Thanks a lot! Well, I guess I decided to invest some time (and not so little) in documentation - perhaps, the first time in my coding life! lol

Main question that remains after reading all that, at least for me, was how do all these features work together, how does it feel to write something bigger in Arturo and how it compares to other languages. Or one way to put it is: ok these are features, but what are the benefits? Why is it cool that it has these features? I guess I should check the examples and try to write something bigger myself :), but I didn't get there yet! But on the other hand I am sure there will be more people like me who don't have time and might forget to revisit it later, so that is why I am mentioning this -> it would be great to offer them that information in shape that is easy to consume, so they get interested.

I absolutely get your point. Most people, except if they are themselves language designer or something along these lines, have very short attention spans - especially with new languages/technologies.

So, I'm totally taking your opinion into account. And I will add a section like the one you suggest. I just waited a bit more, until the language - or better said, its implementation - takes a more "complete" shape.

For example, the idea of it being "mother of all DSLs" sounds very interesting, but I am not sure why is that so, what makes it very good for that purpose? This is probably due to my lack of experience with DSLs (although I am writing one :D!) and no knowledge of Rebol paradigm hm.

I feel now like I am babbling a little bit, but to sum it up, I would suggest putting benefits / vision in structured manner in the documentation, to make it easier for people to get involved into the project (and excited about it). That said, it might be that people who will be most interested in using it for DSLs don't need that kind of explanations, and it is just that I am not a target audience.

That's an interesting catch. When I designed Arturo, I just designed something totally from scratch. Now, I have promoted the language as "Rebol-inspired", but the absolute truth of the matter is: when I started out, only thing I knew about Rebol was its name (lol) - I just created something whose syntax ended up being to similar to something that already existed. I guess you could call that "re-inventing a wheel I didn't know it was there".

Let me illustrate a couple of things (and what I'm saying is not even Arturo-specific, the exact same idea would be pretty much valid in any language of the Rebol group: Rebol, R3, Ren-C, Red, etc)

Let's take this: this is a sentence. In English, it would be a sentence, that is: a sequence of "words". If you understand what it means, it's because you know the meaning of the words in a specific context (the English language). However, if I isolate for example the word a, this in Spanish would mean "to". In a few words, it all depends on the context (or the "dictionary" we are using). It may mean this, or that. Nothing is predefined. Until it takes some meaning, it has none: they are just "words". Or to be precise: everything is just blocks (lists) of something (words, symbols, etc). That's exactly how things work in Arturo.

Basically, you could say there is no syntax whatsoever. That gives pretty much total freedom. And that's a basic ingredient for creating DSLs.

Have a look at this:

Screenshot 2020-11-11 at 06 20 22

Replacing Electron and Flutter - wow those are ambitious goals, but you seem to be well on your way towards it, I am excited to see how will that evolve :)! 100 languages -> I agree, this is in big part reason why we started doing Wasp -> web dev is suffering a lot from having to use a ton of different technologies to build even smth very simple. Although, I do think there is also some sense in using DSLs for specific purpose (well of course it does, it is in their name :D!), and actually web dev is actually a pretty complex thing in its essence -> GUI, multi user system, network delay, possible sudden need for scaling resources, ... -> it makes sense to have DLSs for specific parts of it. The problem is in how well are those DSLs integrated with each other, how easy is it to use them together, and how much time do we need to spend to get them working seamlessly with each other. And certainly one solution to that is to have them be embedded DSLs - really just libraries in a single language.

Well, that's exactly what I've been thinking of! :)

Contributing to Wasp -> well that is awesome, you would be our first contributor :D!! If you want to learn some Haskell, it could be a good opportunity: as you said, project is still relatively small, and another thing is that we are not Haskell masters, so we mostly use relatively simple features ("Boring Haskell"), it shouldn't be hard to grasp the code and add to it (we even have "good first issue" issues :D!).

I see your point and it was a great idea. There's no better to become totally comfortable with a new language/technology than working with it. And Haskell, seems definitely on the rise. And for good reason. The reason I didn't choose it is that (a) as I said, I don't consider myself fluent enough and thought that it would have made things much much slower for me, (b) if we are talking about creating an interpreter, AST-walking, or bytecode-generating VM, speed matters - I have thoroughly and exhaustively tried and benchmarked every language candidate: C beats them all. Then I considered the more... modern alternative compiled languages that could in theory "compete" with C, namely: Rust, Go, Nim, Zig, Crystal, Haskell, D, etc. Haskell - or its implementation, to be fair - was unfortunately on the slow side.

Oh and I saw your PRs, very exciting, we will respond to them as soon as we can, thanks a lot :)!

I'll start studying your code a bit more and try to contribute something even more... substantial! :)

Nim -> I keep hearing about Nim lately, now I am thinking I should probably take some time to learn more about it! Sounds like a good choice from what you explained and from what I just read.

It is. If you need great performance, and less headaches than you'd have with C, it's absolutely the way to go. The only negative point for me is how much it looks like Python - but I guess I've gotten used to it by now lol (yeah, I know, I must be one of the few programmers that absolutely avoids some of the traditional holy grail languages: Python, Java, C++)

Ha it is great to hear that you liked Croatia, I have also been to Greece just a couple years ago and it was very fun, I learned how much I love greek salad (yum feta cheese) and now I eat it very often -> healthy, tasty and quick to make so you can spend that extra time on programming :D!

I've been living in Spain almost for the past 6 years, but yes - feta is a good thing. The even better thing is that we can still find it here! haha.

Martinsos commented 3 years ago

I have to admit we didn't worry too much about speed, especially since we are compiling/transpiling and not interpreting, but let's hope it doesn't bite us back at some moment. Although I would be very happy if we reach that tier of problems :D. Language-wise, Rust and Nim sounds to me like something exciting I should look into in the future, and C/C++ and Javascript are kind of always needed sooner or later, I keep revisiting as needed -> ah, so much fun stuff to learn and so little time :)!

Rebol and words

Thanks for the explanation, I read the part in docs explaining it in similar fashion, saying it is all words that have no meaning by itself, but instead they are assigned the meaning in a specific context. That sounds exciting and I can imagine that to some point, but then I fall short of figuring out how that plays out in practice, what is it useful for. Naturally, I try to connect it with what I already know, and the closest thing I can think of is (e)lisp. I don't have much experience with lisp, and if asked I would say I don't know it, but I do use some of the elisp when configuring emacs so I naturally worked with some of its concepts, and I know that the variables have name in kind of a symbol fashion and they can be passed around either as a name or as a value, smth like that hm, I read about it but already forgot. And regarding them being evaluated later, well that also makes sense, they are passed as kind of a "reference" until they need to be used (lazy computation - I although I haven't seen you using the word "lazy", I guess there is a reason?).

Anyway, based on this, I imagine each word is essentially something like { name, value } in its essence, and that is passed around. How is that different than a typical variable in JS/C/... ? I guess the main difference is that its name it part of its runtime value, and therefore very easy to access and to work with? So let's see the code:

type sentence

It makes sense that this works, it does not need to know what is inside of the block and never tries to evalute any of the values in it, so all is cool.

print first sentence

Alright, so print I guess is a word that has function as a value and is part of core library or it is a builtin, first I assume is same as print -> a word with name and function as value, and that function takes the first word from the block, and sentence is a word with defined name and value. What I guess is that interpreter due to precedence starts evaluation with first, says aha it is function, and then starts consuming needed amount of words after it, which is 1. It returns first word from block (not evaluating it, because why should it). Then print is evaluated, and print cares only about the name of the word it was given, so it prints its name, doesn't touch the value.

So far, this to me sounds like laziness (which I know from Haskell) but with dynamic typing -> which sounds like lisp (which I admittedly don't really know :D).

do sentence

Ok, so here I guess that do tries to evaluate given word. Since it is block, it starts evaluating word by word. It tries to evalute the value of each word, but this is where the "problem" happens -> there is no value, so it complains. Makes sense.

do [print "Hello world"]

Ok, this also makes sense.

So the code example in total makes sense, but I still didn't understand from it why is it cool to have this functionality and how it enables building DSLs with it. Btw. I am not questioning that it does, I believe you that it does :D, but I personally don't understand why/how -> I am just trying to describe my perception based on the docs/explanations.

What would be a cool example of smth Arturo can do easily, thank to his Rebol/lisp-inspired design, that would be uglier/harder/impossible to do in some other language? I saw html and bootstrap module, and while I can see the result is an elegant way to define html in it, I wonder how that compares to some other language. I am immediately thinking about Haskell, and I am thinking ok, stuff like html [ head [ ] body [ ... ] ], I can do that easily in Haskell, where html head and body are functions and I just invoke them on lists of stuff and they return some kind of HTML AST. Ok, I see attributes as potentially interesting though, in Haskell it is not easy to have optional arguments/flags, since it is all strictly typed. There are ways to do, we would probably define a configuration data type, define a default value for its fields, and then modify those that we want to, it would at the end look like serve (serverConfig { verbose = True, port = 18966 }), which is certainly not as elegant as what you have with attributes. Ok, so attributes are certainly a good point!

TLDR: Cool, now I understand better! What could help more is more concrete examples how is Arturo great for DSL compared to other languages(s) -> which features exactly, and how (show in examples) make it good for this purpose.

Btw. I understand it might be too early for this kind of docs if everything is still changing a lot, but maybe you will be able to use this feedback later when you get to it!

drkameleon commented 3 years ago

@Martinsos Lazy evaluation - as you yourself have pointed out is at the heart of Arturo. Basically, everything is "lazily evaluated" and re-definable.

That's part of Rebol's expressive power.

However, I still get why it might be a tiny bit not easily approachable at first. I must absolutely add examples to showcase this as you said, I'm just trying to do it step-by-step while I'm still solving little issues here and there.

But in any case, you do have a point ;-)

Martinsos commented 3 years ago

No prob, I hope this helps at some point!