8 ms·
Pen: A programming language for scalable development
- staticassertion 5y agohttps://pen-lang.org/examples/types/function.html https://pen-lang.org/examples/types/function.html Took just a bit of searching to find some code examples.
- pknerd 5y agoThese black slashes looks so weird
- cies 5y ago...it's more popular with languages using the "ML" syntax. https://en.wikipedia.org/wiki/ML_(programming_language) https://en.wikipedia.org/wiki/ML_(programming_language)
- Zababa 5y agoIt's not the ML syntax, it's almost only a Haskell thing, and while Haskell is a descendant of ML, it's a language on its own.
- Yoric 5y agoafaict, they mean "lambda" I expect that there will be an Emacs/Vi/VSCode/... mode to render them as such.
- amw-zero 5y agoReally, this is why we can’t make any progress. Because this is such a common response to anything. Go back to when you learned your first programming language. EVERYTHING was weird. I honestly don’t understand how after that, brains solidify and think anything after their first year of learning is weird.
- saulrh 5y agoAnd I can't find a "hello world" or example project at all...
- jitl 5y agoI don’t need to spend any more time with static typed languages that avoid generics. I wrote Go for several years, tried to love the simplicity, then tried to love code generation. Then I gave up. I don’t need to repeat that experience.
- raviqqe42 5y agoI agree. It's not for everyone but there are many different kinds of developers. If you are and can hire smart people who can use generics without introducing extra tech debt and complexity, I definitely recommend the ones with generics like Rust and Haskell. But the problem is that I'm not smart enough.
- techsin101 5y agoAs JS developer it took me sometimes realizing the importance of generics, as by default in JS problems it solves doesn't exist. Funny how typed language advocates want automatic casting in the end after all.
- bitmapper 5y agoSince when are generics automatic casting?
- techsin101 5y agoit's not but it's essentially the same practically speaking -- you get type A|B|C you write code to interact with it in just one way. Either by casting, or generics. weakly typed language do that for you, but they are looked down on.
- myoon 5y agoI think you're missing the key point of statically typed languages, that the compiler catches errors for you. Generics are valuable because it allows users to write "generic" reusable functions that are still checked by the compiler. Of course dynamically-typed languages can do this easily, but that's not the point.
- SkyMarshal 5y agoTLDR: > Pen is a statically typed functional programming language for application programming with system injection. Its design is heavily inspired by the Go programming language and many functional programming languages like Haskell and Koka. ... Pen aims to be even simpler [than Go] by ... removing several features from Go like pointers, mutability, method syntax, global variables, circular references, etc. ... Pen's approach to that [maintenance] is embracing battle-tested ideas in such field [software engineering], such as Clean Architecture, into the language's principles and ecosystem. One of its most clear incarnations is system injection. System Injection: A mechanism to inject system functions into pure functions, eg a dynamically typed effect system (https://github.com/pen-lang/pen#system-injection https://github.com/pen-lang/pen#system-injection)
- linux2647 5y agoI’m all for experimenting with languages, but there is something to be said for having a familiar syntax. Using & and | for Boolean logic operators could be seen as a useful improvement, but then how does one express bitwise and and or? Additionally, all numbers are floating point. Would there be any future support for native integers? Handling currency with floating point has long been known to cause rounding errors. Despite that, it’s interesting to see a language put dependency injection at the core of the language. I’d be curious to see how that works out in the long term.
- deleted 5y ago[deleted]
- raviqqe42 5y agoIMO, dependency injection tries to solve similar problems which are traditionally tackled by purely function programming languages, such as side effect management, reliable unit tests, segregation of application logic and implementation details, and so on. This is too rough but, in other words, dependency injection is simply a less strict or untyped version of effect system or purely functional programming.
- adrian_b 5y agoOne of the innovations brought by the C language was the use of distinct symbols for the McCarthy logical operators (&& || !) and for the bit string operators (& | ~). The predecessors of C, i.e. B and BCPL also had both kinds of operators but they used the same symbols for them (in B: & | !) and the context determined which was meant. However the choice made by C for the new symbols was constrained by the ASCII code, which had no other available symbols. One decade before the C language, there were 6 symbols in use for the 3 logical or bit string operators, for example IBM PL/I used & | and NOT SIGN, while CPL and IBM APL\360 used LOGICAL AND, LOGICAL OR and TILDE OPERATOR. The names in capitals are the Unicode names of the symbols. So there are enough traditional symbols for both the McCarthy logical operators and for the bit string operators, without inventing any new symbols, like C did. In my opinion, the IBM PL/I set of 3 symbols (& | NOT SIGN) is appropriate for the McCarthy logical operators, while the CPL / IBM APL\360 set of 3 symbols is appropriate for the bit string operators. The reason is that & and | are more visually distinct so they are preferable in IF or WHILE conditions. On the other hand, the bit string "and" and "or" are nothing else but "min" and "max" applied to vectors of 1-bit numbers. So the symbols LOGICAL AND and LOGICAL OR are also the right choice as symbols for "min" and "max". Because the LOGICAL AND and the LOGICAL OR symbols are just rotated LESS THAN and GREATER THAN, they are graphically suitable for "min" and "max".
- bitmapper 5y agoI cannot comprehend what would drive someone to make this.
- raviqqe42 5y agofree time haha
- bitmapper 5y agoFair enough! Sorry, I didn't intend that to be rude, I just genuinely didn't understand as it seems to be two very conflicting ideologies merged.
- pharmakom 5y agoI think this project is a great idea! A minimalist run-time and language (like Go) but with an emphasis on functional programming seems like the best of both worlds! However, will the language get cumbersome without advanced FP features? See Elm debates…
- bitmapper 5y agoHonestly, my main issues are with the lack of generics and the "dynamically typed effect system". The idea of a minimalist runtime and language reminds me of Clean a little bit.
- ram_rar 5y agoI love new programming languages and the concepts they bring to the table. But I feel PL designers should think about Dev experience. Is it just me or is the "\" in front of parenthesis (func params) is just off-putting. I wonder, what purpose does it solve? Familiar syntax makes it much easier to adopt and easily convince devs in your team to try it for real.
- cormacrelf 5y agoProbably looks like lambda. Haskell has them. \x -> x + 1
- ulrikrasmussen 5y agoI agree, but lambdas do not really have a canonical syntax in the same way that braces have become synonymous with delimiters for statement blocks. This particular syntax comes from Haskell, where e.g. \x -> f x denotes an anonymous function that applies its first argument to `f`. But I have seen at least these forms in other languages of varying popularity: [x] f x |x| f x { f(it) } { x -> f(x) } fn x => f x function(x) { return f(x); } x -> f(x) (x: A) => f(x) In other words, I think it is really hard to pick a syntax for this construct that every programmer is going to feel familiar with, especially if your language is supposed to cater both to programmers coming from FP and more traditional languages. Edit: Fixed error in JS example; added Java and Scala.
- chrismorgan 5y ago> function(x) { f(x); } Slight correction (presuming JavaScript): that’d be `function(x) { return f(x); }`.
- ulrikrasmussen 5y agoThank you, fixed!
- marcle 5y agoThis could also be R, which allows for `function(x) {f(x)}` and (since version 4.1) `\(x) {f(x)}`.
- gorgoiler 5y agodang / raviqqe42: I believe this is a [Show HN]. everyone: reminder of the very good Show HN guidelines regarding expectations from submissions and those offering feedback: https://news.ycombinator.com/showhn.html https://news.ycombinator.com/showhn.html
- 6gvONxR4sf7o 5y agoI’ve never heard of Koka before (one of its stated predecessors), but Koka seems really intriguing. Has anyone used it?
- cies 5y agoSuper cool indeed. I learned MSFT pulled funding for this project. Sadly.
- anfelor 5y agoNo, that seems wrong. Its currently only Daan working on this, but as you can see the last commit to 'master' was 7 days ago and the last commit to 'dev' yesterday...
- cies 5y agoSo was there MSFT funding? And is there now MSFT funding? That it gets continued as a hobby project does not mean it was not funded at some point (and is no longer). But I'm not sure about my statement; no source also (just remember reading it). CORRECTION: as can be read rest of the thread, Koka is being funded by MSFT.
- anfelor 5y agoDaan is employed full-time at MS Research and gets to spend this time on Koka (when he is not writing conference papers). There is currently no further funding or deployment of Koka within Microsoft that I know of (unlike mimalloc which seems to be used by Azure and Bing).
- cies 5y agoThanks for setting this straight!
- anfelor 5y agoYes, I am currently writing a masters thesis about it! It is a "research language that [is] currently under heavy development" as the README says so I don't recommend using it for anything other than a research/toy project. But you would be surprised how well it works: Algebraic effects can give you 98% the power of monads while being much faster and easier to understand. And then Koka uses mimalloc [0], Perceus [1] and tail recursion modulo cons which make Koka programs almost as fast as C++. For example, in the benchmarksgame, Haskell takes 5x as much time on the binarytrees benchmark as the fastest implementation, while Koka is 50% slower (similar to other C/C++ and Rust implementations). [0]: https://github.com/microsoft/mimalloc https://github.com/microsoft/mimalloc [1]: https://news.ycombinator.com/item?id=25464354 https://news.ycombinator.com/item?id=25464354
- lawl 5y ago> It pursues its minimal language design further after removing several features from Go like pointers, mutability, I don't consider pointers and mutability to be features, but I consider immutability and trying to hide pointers a feature. One that I don't want. Allocating too much/too often has been like 95% of the performance issues i had. Computers use pointers and data in ram is mutable. How is pretending that's not the case removing a feature? It's the exact opposite. One of the reasons I like go is that I can have some control over memory when necessary. But most of the time I don't need to think about it unless the profiler tells me that's where the bottleneck is. Small edit to not be so negative: The language looks interesting and I think it's well presented. Just not for me, and that above irked me in particular.
- grumpyprole 5y agoModern machines are essentially distributed computers, multiple levels of cache per core, RAM allocated per core. The flat shared memory address space is an illusion. With such an architecture, immutability and not exposing pointers is a very reasonable approach for many parallel/concurrent workloads. It enables many optimisations. An algorithm written for such an abstraction is also much more easily adapted to work across multiple machines (e.g. map-reduce).
- anfelor 5y agoSince Pen claims to be inspired by Koka, I would hope that they eventually implement Perceus reference counting [0], which (partially) solves the problem of too many allocations. The idea is that with immutable datastructures you often free a constructor just before allocating the same one again (for example during a map function). But with reference counting we can check if the old constructor is dead and if so use it in-place for the new constructor. Applied carefully, you can build functional programs that use no further memory. [0]: https://news.ycombinator.com/item?id=25464354 https://news.ycombinator.com/item?id=25464354
- curryst 5y agoI didn't think there was a massive memory gap between functional languages and other paradigms? I had always made the assumption that it was because immutable data allows the compiler to make optimizations that it normally can't. For example, you could pass all values by reference implicitly, because they can't be mutated. There are probably others. It seems like the paradigm is different enough that the pitfalls are also slightly different.
- cies 5y agoI miss a serious examples section. I have no idea what it looks like from merely reading the reference docs.
- moffkalast 5y agoThe real question: is it really mightier than the SWORD
- PeledYuval 5y agoI appreciate the stated goals of Pen. However, I don't see how these goals translate to language design. Anybody tried the language and can share how the design facilitates these goals more so than other languages? - Everyone can learn the language and participate in actual development quickly. - Developers can focus on application logic rather than ever-changing implementation details.
- bruce343434 5y ago> It pursues its minimal language design further after removing several features from Go like pointers, mutability, method syntax, global variables, *circular references*, etc. So no graphs? Or more complex data structures?
- raviqqe42 5y agoWe can still represent graphs expressing references explicitly, for example, using hash maps. Here, I just wanted to point out no circular references "on memory" in the language. It might be interesting for you to take a look at documentation of Rust or Koka and how they represent those data structures!
- xupybd 5y agoWhat does it take for a language is like this to get enough critical mass to be the kind of language you don't get fired for choosing?
- evnix 5y agowhat I liked about this and would want Go to pick up is error handling. Rust's ? expression is probably one of the best inventions from the last 2 decades. There is more error handling code in my Go project than actual business logic. I see hundreds of error handling proposals being shot down by the Go community, I am not sure if these people write the Go compiler or the ones actually using Go to build projects or is it the case of, "since I had to suffer with error handling, you should too."
- Jeff_Brown 5y ago"System injection" is apparently the major novelty in this language. But it's not described in detail, and I'm not finding it on Google. What is it? Is it important?
- tramjoe_ 5y agoFrom what I just saw on their website it looks like an other way to implement what an IO monad in Haskell gives you, which is to write code that pretends functions that in reality have side effects are pure. This is achieved in part by passing around some Context (World in Haskell) that encapsulates the "state of the world" onto which the side effects act upon.