I just finished PolyConf, a two-day "polyglot programing conference", and I'm really excited. There were a lot of really interesting talks so I want to share it all with you. Here are some of the things I saw:
A guy from Wunderlist team talked about using 10+ different programming languages on production. Apparently they have a lot of microservices. Some interesting takeaways: if you write it, you run it (and that includes convincing other people to learn your language!); and a service should be simple enough so that (as a last resort) you will be able to recreate it in one day.
Interesting talk about teaching programming to people with completely different backgrounds (e.g. humanities). Apparently you will struggle with lack of mathematical rigor and basics (such as computational complexity). On the other hand, you get a lot of "domain knowledge" when cooperating with them, and (not sure if that's a plus) they are much more willing to do repetitive tasks than us lazy programmers :)
Very nice lightning talk about Commodore 64. The guy showed us a program in assembly: look, here is this program, it runs in a loop and does this animation. But then I take the address of this loop, and put it in an interrupt handler, and look! It still executes but I can type text at the same time! So we get asynchronous programming on an 80s machine.
Good insight from Elasticsearch guys that decided to make their HTTP API more accessible - they said that "clients are part of the distributed system" and decided to write the clients for their API in various languages as well, to ensure that the users will have a good experience with Elasticsearch. Then they were able to adapt one test suite to all these languages.
A demo of immutable data structures in Clojure. You can have an immutable "vector" (internally a tree) that you can modify with a (small) logarithmic overhead, and keep both versions around, sharing the common parts. Sort of like Git. So for instance you can have an editor storing all versions of a file and effortlessly add undo-redo functionality. I really want to use all this to make a time-travel game sometime.
An interesting but quite frightening talk from a manager in an "agile company" - a large Poznań-based Python software house (STX Next). Highlights: whole team in one room (nice!), there has to be a woman in every room (ok…), everyone uses time-tracking (uhh….), there are huge screens everywhere and every employee is on camera (get me out of there).
A talk about NoSQL and domain-driven design. I think I undestand more about what the fuss is all about - it's not about being able to store amorphous, complicated JSONs, but the fact that value objects (e.g. price+currency pair) don't really make sense as database tables; and relational joins don't have to be the only way of representing relationships. (Well, also scaling.)
Awesome coding session with a guy making snake game in ClojureScript (another language compiled for the browser). He was really excited about being able to hot-swap the code in browser without having to reload (and keeping the state), enthusiastic about Paredit mode in Emacs, and got everyone fired up about the technology. "Can I have two more minutes? I can make it eat berries in two minutes!"
A talk about cross-platform Ruby being translated to all different technologies including Arduino and Objective-C on iOS. Also with a healthy serving of "hexagonal architecture" thrown in (write platform-agnostic code and write "adapters" for absolutely everything external). Sounded like too much of a good thing, to be honest…
At the end, a great presentation of automated test generation by John Hughes of QuickCheck fame. He told us "don't write tests - generate them!" and presented the approach on several examples, ranging from a toy circular-buffer program in C to verifying huge amounts of code in automobile software based on a 3,000-page standard. We have a rudimentary tool here at Codility for challenges, maybe it's time to resurrect it?
And that's not even mentioning everything (there was also F#, some Rails Girls and PyLadies, a few more philosophical talks…) So all in all, a great conference that I'll definitely attend again next year.
I hope you enjoyed this write-up and feel encouraged to attend more events like that!
The examples are "very Java" at times, and you might not agree with all the choices the author makes, but don't be discouraged: the book gives you some very useful principles about how to structure your code, split it into simple parts, and generally avoid making a mess (I think the most valuable one was operate on a single level of abstraction at a time). The book includes real-life examples that are really helpful for understanding.
Overall, I think my time reading this book was well spent.
Some important points:
- "The folks who think that code will one day disappear are like mathematicians who hope one day to discover a mathematics that does not have to be formal."
- (Michael Feathers) Clean code looks like written by someone who cares; there is nothing obvious you can do to make it better.
- Tests have different requirements than production code but have to be kept clean as well, or it will impact your project seriously.
- You should be able to describe what your class does in a simple sentence that doesn't contain any "and"s or "if's.
- Refactoring "is like solving a Rubik's cube" - you have to make a lot of small steps, not always straight to the goal.
(adapted from a post on Reddit)
I recently wrote a seven-day roguelike in Lua. It was my first project in Lua, and second roguelike (after coding one in Python a year before). I don't have much to base this on, but believe dynamic languages like this are the fastest and best way to write a roguelike game. You write relatively little boilerplate and have much freedom with how to design the engine, compared to, say, endless classes bureaucracy in Java or manual memory management in C.
Coming from Python, several things irritated me. The language feels lower-level. There are less primitives available from the start. Everything takes more code to write. While the tables are a nice concept, often I missed working with real lists, tuples and arrays. Also list comprehensions, everything being a sequence. Ternary if. Multiple return values, and unpacking, instead of simple tuples. Optional arguments… the list goes on.
Most of the things I wanted I could actually do in Lua, but it seemed more verbose and more prone to failure. Of course, in part this is probably due to my inexperience. And I was probably trying to mimic the previous (Python) engine's architecture too closely.
I loved being "close to the metal" - actually understanding how the tables/methods I use actually work. Classes in Python feel too heavy sometimes (and definitely more magical, harder to understood, and uglier). In Lua, the whole thing seems very malleable. This is a language you can make every object system you can think of, after all.
As for having to define all the OOP-style mechanisms from scratch - this is, IMO, a non-issue. After writing an object system, using it was as easy as everywhere else. I even managed to hack some field-imitating class properties.
It frightens me how easy it is to make an error in Lua. All it takes is to forget a
local before a variable, or mix up
foo.bar() - and the error may not surface at all until much later (unless you bother to make tests… I probably should have): the system doesn't complain if you do
.bar() instead of
:bar(). It doesn't complain if you give it wrong number of arguments. Reading an uninitialized variable gives you a silent
nil. Bugs not failing early enough are a problem in most dynamically-typed languages, but somehow in Lua it seemed especially bad.
(Some of these are fixable, for example you can easily forbid making global variables, ensuring that leaving out a
local will blow up).
There is no built-in module/namespace system, just loading files. Well, actually there is the module() function, but from what I've read, it's considered deprecated and harmful…
Numbering arrays starting from one is an ugly wart. Of course, everyone tells you that you get used to it, and they're probably right… but I haven't seen any argument about it being superior, just about not being important. Still looks ugly. Especially when if you interface with a library that counts from zero. But this is nitpicking, the language seems very well designed apart from that.
Keep in mind that I'm a beginner and I don't know what I'm talking about. If I stayed with Lua for some more projects, I probably would've stopped whining about it not being Python and learned to appreciate it more. Also, the experience wasn't as bad as my negative comments here would make it seem.
tl;dr Try it.
(originally posted on Reddit)
This is a story of Vicious, a human assassin who managed to save the world.
As he enters the Drakalor Chain, he has no name yet… He will have to earn it.
Starting equipment. Not bad, I think. We'll start with daggers - both in melee and thrown.
Ogre mage - has invisibility and frost bolt. I was certain the death is close. Fortunately he turned out to be friendly…
Somehow I managed to reach Dwarftown. As you can see, dwarf grandpa's first quest is a rather easy one.
This is me having some trouble with the animated trees. I seriously thought I'm out of luck when they suddenly refused to let me pass. Fortunately when I calmed down, the solution turned out to be simple - potion of invisibility.
Rehetep, the mummy lord, was quickly dealt with. Assassins are very good at shooting.
The character has been quite successful, I think he deserves a name. Meet… Vicious.
Trying my luck with steel golems in Darkforge. As you can see, a bad idea. I could damage them only with arrows of construct slaying and they quickly run out.
One of the golems refused to let me go. Fortunately…
Most of the time "True Aim" and "Thunderstroke" are useless shit. Come on… artifact ARROW? But somehow this time, being the weapon with best damage I had, it proved quite useful - shoot the golem, run around, pick up the arrow, shoot it again…
Digging some graves on the dwarven graveyard. No good loot, only a troublesome master lich sleeping in one of them.
My visit to Gremlin Cave was more fruitful - I managed to find seven league boots. A very useful item - doubles your movement speed.
You have reached the bottom.
This is how you usually enter the Rift - Climbing at 100, and still the landing is quite hard.
Having in mind the sad story of Tesuji the drake assassin (destroyed his only climbing set in this jump, then spent rest of his miserable life trapped beyond the mountains trying to find a new one - and finally petrified by a gorgon) this time I took two climbing sets. Both survived the fall.
And that's why you enter the rift. Awesome library filled with useful scrolls and books. And, sometimes, artifacts - here I found the sapphire amulet "Preserver".
Drinking from pools can get you a free wish. Or a dooming curse. They say the probability is the same. Somehow, I don't believe it.
This was scary. Never fall asleep at the wheel. I started playing "on autopilot" and suddenly found myself face to face with a gorgon. One more turn and I would turn into a statue.
The Casino. Lots of gambling machines and a huge shop. There is a way to get practically unlimited money playing on the machines - just find the best one, put something on your Enter key and wait some time… I consider it terrible, anticlimatic farming bordering on cheating.
Cat Lord was generated when I had 18 cat souls on my conscience. I was afraid direct confrontation would be my end - so I Acidballed him through a wall :)
Acid Ball rocks. Did you know you can kill even the Elder Chaos God with it?
A room full of Ghost Kings… If I started to fight them, the poor human would die of old age in no time… Fortunately I managed to escape without being noticed.
And for a good reason - these greater vaults often contain artifacts and much good loot. Not to mention lots of exp.
Here we see a vault of fire creatures - dragons, fire elementals and such.
This is me remembering that fire burns. That was my best bow…
One more extremely annoying location - the blue dragon caves. Full of lightning-breathing dragons ready to destroy every burnable item you have.
But for killing this fellow I get a certain rune-covered dagger called "Needle". And once I obtain another one called "Sting"… Neither of them is very powerful on its own. But when I wield both of them:
Right hand: +230 bonus to hit, 3d4+116 damage
Left hand: +228 bonus to hit, 3d4+116 damage
Sting & Needle - the deadliest combo in the game.
Emperor moloch in his castle. In all his armor he's like a walking tank. I guess assassin's arrows are better than anti-tank missiles.
Time to save the world!
First time a balor has ever surrendered to me. I had to kill him anyway - he kept opening the Chaos Gate and I couldn't leave the level with him around.
This time I wiped out the whole level. For a moloch-armor-covered (81 PV!), Sting-and-Needle-wielding walking tank it was very easy.
Photos, full recording (in DOS Recorder) and final savegame
I think this was the strongest PC I ever played. High-level assassin is easier than a barbarian. And because of Backstabbing and other class skills he doesn't even need an artifact/slayer weapon - he manages to score critical hits with everyting. Most of the game, Vicious used a plain sword of sharpness.
Hope you liked it!