Showing posts with label dotnet. Show all posts
Showing posts with label dotnet. Show all posts

Tuesday, September 04, 2012

Second Thoughts on C# and .Net

I got quite optimistic about nSuneido - a .Net implementation of Suneido. The C# language is decent, the Dynamic Language Runtime (DLR) looked promising, and Mono and MonoDevelop were better than I expected. I went quite a bit farther with my experimenting than I had with D.

But ... I started to run into some frustrations. First, the MSDN .Net documentation sucks. That wasn't a big deal when I was just writing simple code. But when I needed to use the framework, it wasn't so good. Granted, I was trying to work with memory mapped files, which is often tricky. And some of the problems may have been due to working in Mono, rather than on Windows. I ended up having to look at the Mono source code to figure out how to get things working.

Looking at the source code made me realize that Mono probably isn't quite as production capable as I would like. Don't get me wrong, they've done a great job, but unfortunately they'll always be a second class citizen playing catch up with limited resources.

Don't get me wrong, I realize there are going to be frustrations with any platform. The grass always looks greener than it actually is. You initially tend to focus on the problems that something will solve, not realizing what you might lose, or the new problems it will introduce.

Finally, I started to wonder if I really wanted to support multiple implementations. I realize that I actually chose quite well when I picked Java. I don't think there's any question that the JVM is the most stable, portable, and performant platform.

So why was I looking for an alternative to Java? There are two main things:

- Suneido's current user interface is Windows API based

- The Java language is ok, but it's ... old. We can do better.

(There are other issues, like the lack of fixnum's and value types, but you can't have everything.)

But it may be possible to solve both of these, and stay with the JVM platform and all its goodness.

- Java Native Access (JNA) can provide access to the Windows API

- Other languages are available on the JVM (more all the time). I could use Xtend, or Scala, or maybe Kotlin. And using another JVM language could be done incrementally.

I'm a strong believer in not starting software projects over from scratch. And I don't believe that's what I've done with jSuneido. Porting or writing an alternative implementation are not the same as starting from scratch. What I've found, especially lately, is that rewriting existing code, even multiple times, is very beneficial. You find bugs, discover better approaches, and gradually work towards a clean design. The jSuneido implementation is much better than cSuneido. And from rewriting code in Xtend, and D, and C# I continue to find better approaches.

I don't want to give up the benefits of rewriting, but I also don't really want to write and maintain multiple implementations. Perhaps sticking to the JVM and experimenting with alternate languages is the best compromise.

Thursday, August 30, 2012

nSuneido DLR Spike

After getting a C# version of the lexer working I decided to take a stab at the parser.  Suneido uses a hand-written recursive descent parser so it's pretty simple code to port.

I've been doing some reading on the dynamic language runtime (DLR) so before implementing the complete parser I decided I'd push a spike through to actual code generation.

This turned out to be remarkably easy. Rather than tie the parser directly to the DLR methods, I created a ParseOutput interface. For testing I wrote a simple AstNode class and a corresponding AstOutput. Once the parsing was working I added a DyExprOutput class that creates a DLR Expression tree, which you can then compile via Expression.Lambda (see the tests at the bottom of DyExprOutput).

source code at GitHub (the link is to this specific version, you can navigate to the latest)

This only handles very simple expressions - math on numeric integer literals. (It doesn't handle even as much as the partial parser does.) But to get that far in Java took me way more work.

I found one book on this - Pro DLR in .Net 4 - which has helped. There's also quite a lot of material on-line.

Another nice feature is that the DLR is just a library - it doesn't involve any .Net internals. And even better, it's open source on CodePlex. It's troubling that it hasn't been worked on since 2010, but since the "dynamic" keyword in C# uses the DLR, I assume it won't be going away.

So far, I'm still quite positive about C# and the possibility of nSuneido. My primary motivation is that cSuneido is falling behind jSuneido, but I'm really not keen on doing a lot of work on the C++ code. And even if I did, it wouldn't solve the garbage collection issues. And we can't switch to jSuneido for the client because of the current Windows specific GUI.

Sunday, August 26, 2012

nSuneido ?

It's been a long time since I've looked very closely at C# and .Net so when I saw a special on the C# 5.0 Pocket Reference I figured I should catch up. I read it cover to cover, and surprisingly (to me) I was quite impressed. C# has come a long way since version 1. It's certainly moved much faster than Java. In my recent System Programming Languages post I discounted C#, but I'm starting to wonder if that was a mistake.

* "nSuneido" comes from the convention of using 'n' for .Net projects e.g. NUnit, NHibernate, etc.

I also picked up C# in Depth by Jon Skeet (of StackOverflow fame). It was perfect for me because it covered the evolution of the language, not just how to use it.

One concern with C# and .Net is portability. But Mono seems to be in good shape and in active development. So far all my playing with C# has been on the Mac with Mono and  MonoDevelop. Of course, Mono lags somewhat behind - it's on .Net 4.0, whereas the latest is .Net 4.5. And it's performance isn't quite as good, but it's not bad.

There are a lot of things I like about C# and .Net (in no particular order)
  • It meets my mandatory entry level requirements of safety and garbage collection
  • Unlike Java, it has value types (in addition to reference types)
  • Like Java, .Net has a VM and IL (byte code) that Suneido can target
    (whereas with native languages like C++ Suneido has to implement its own VM)
  • Stable, robust, performant platform
  • Rich ecosystem of books, tools, libraries, developers, etc.
  • Easier to find programmers who know C#
  • Extension methods 
  • Class members and fields default to private 
  • Decimal floating type (one less thing to implement)
  • Lambdas :-)
  • Delegates (method handles) 
  • Named and optional arguments
  • Type inference (var) although only for local variables
  • Dynamic language runtime (DLR) 
  • Good access to Windows API's (PInvoke)
  • Annotations
  • Anonymous types and tuples
  • Operating overloading
  • Nullable (a bit like Scala Option)
  • Unsafe code if needed
  • Good IDE support
  • Generics on unboxed primitives (unlike Java)(no need for Trove collections)
  • Reified generics (unlike Java)
  • LINQ
There are, of course, some things I don't like. I'd really prefer optional semicolons (like Scala and Go), but I can live with them. It's taking a little getting used to capitalizing public methods and fields even though this is similar to Suneido. I miss Java's static imports - there's no way (that I've found) to have something you can call as simply Foo(). It always has to be Something.Foo()

With Java I could get almost all the tools and libraries I needed open source. With C# it seems a lot more commercial. Visual Studio and popular add-ons like ReSharper and Reflector are all commercial products.

I'm maybe just not up to speed on the C#/.Net ecosystem, but it doesn't seem like there aren't as many good libraries available. I would miss Guava. I need to learn more about what is and isn't available in the standard .Net libaries.

Once more, I started by implementing the Suneido lexer. This is turning into a coding kata for me, but I still find ways to improve or simplify each time I re-implement it. I took advantage of a number of C# features like extension methods and even lambdas. The code is on GitHub along with the D version. By the time I finished this exercise in D I had lost much of my enthusiasm and was somewhat disillusioned. In contrast, after the C# implementation I was still quite keen. In the long run, that probably doesn't mean much, but it's a good sign. As much as we might like these decisions to be objective it often comes down to subjective factors.

Ideally I would have just a single implementation of Suneido. (There are sometimes advantages to multiple implementations, but it's a lot more work.) Although the Java version is great for larger servers, it's not well suited to the current Windows GUI. And it's not great for smaller servers (e.g. smaller EC2 instances). An intriguing possibility is using Scala on both the JVM and .Net. I really like Scala, and the idea of writing one implementation that could be compiled to run on either the JVM or .Net is very attractive. The .Net version of Scala isn't production ready yet, but it's something to keep an eye on.