Tag Archives: scala

Generic static fields — see you next year

I wanted to make a mental note at the end of 2015 — “feature freeze”. It won’t happen, I cannot make my mind what is the right choice.

The natural decision would be to copycat C# — each constructed type has its own copy of static fields which allows to use generic static fields. Resharper wiki warns about this approach — “in the vast majority of cases, having a static field in a generic type is a sign of an error” ¹. We can find simpler one in Java (more for historical reasons than technical, but still) — it does not support generic static fields and it shares static fields among all constructed types. Scala takes another angle for the same model — since static data can live only in companion objects and they cannot have type parameters the issue is solved by design. As for Swift it is an open question because as the error message says static fields are “not yet supported in generic types”.

C# has some peculiarities — till now I didn’t figure out why C# makes instances of static constructor (see Accelerated C# 2010 by Trey Nash, p.263). Skila would have to add its own because of static variables in generic methods. I feel really insecure here so I wonder whether C# model is worth the effort?

A memento from C++ world:

The original intention of C++ template support envisioned a use-directed automatic instantiation mechanism that required neither user intervention nor multiple instantiations of the same file. This has proved considerably more difficult to achieve than anyone at the time imagined (see [STROUP94]).

— Stanley B.Lippman, Inside the C++ Object Model

Sure, it is not the same issue, over 22 years passed, nevertheless I still have the chills. Until I have firm knowledge or burning desire for this feature I’d better follow Swift footsteps — not supported. Yet.


¹ I was curious what “vast majority” means so I contacted the author of that entry, Dmitri Nesteruk. As it turned out it doesn’t translate to any numbers, it was just a generalization based on the nature of C# model.

Advertisement
Tagged , , , , , , , , , ,

Bringing order to the assignments

I changed the assignments several times — and it is not surprising when you consider the various approaches of the programming languages. Lately I reverted them to “statements only” because of Swift, to change it back to the expressions because of PHP. However the argument statements vs. expressions was not my only concern — I have learned (from Fluent Python by Luciano Ramalho) that Python switches the meaning of the compound assignment depending which operator was implemented in a given type.

m += u;

Will m value be changed in place or will a new object be created and bound to m? It is impossible to say without looking at the m type implementation. Not that I was about to make similar mistake, but I realized that compound assignment should scream its meaning so there were no doubts what it does.

I also have read an interesting complaint about the assignment symbol itself:

A notorious example for a bad idea was the choice of the equal sign to denote assignment. It goes back to Fortran in 1957 and has blindly been copied by armies of language designers. Why is it a bad idea? Because it overthrows a century old tradition to let “=” denote a comparison for equality, a predicate which is either true or false.

I understand the point but I don’t share the reservation — we don’t have the freedom of the blackboard, only the keyboard with just a few symbols. The tool dictates the possibilities.

Enough about the problems — let’s talk about solutions. The assignment is written all over the code — so it has to be single character, for me there is no debate here really, besides there are too many languages which use this syntax, the winner is:

s = "hello world"; 

I would like to compare values with operators like “>” or “<=”, so testing value equality has to be written with:

if s == "hello world" then
  ...

Here is the rub — assigning reference is done with single “equal” sign, while testing the value is done with the doubled sign. Well, far from perfect I know, I know.

Optional assignments work only within conditional structures:

if s ?= tryHello() then
  ...

When tryHello returns null — variable s will not be altered and the true branch of if will not be executed. When tryHello returns real value, the reference to that value will be assigned to s and the execution will proceed.

Assignments used as an expressions proved to be useful, however the usual syntax leads to errors and countermeasures such as yoda conditions. Scala ¹ and Swift ² are examples of the languages that dropped the support for assignment expressions, but why remove semantics when the problem lies in syntax:

a = b := c; // with expression
b = c; // just statements
a = c;

Please note that there is just one edit distance point between “=” and “==”, while there are two points between ”:=” and “==”. It does not guarantee the safety, but it should be sufficient protection against misspelling.

I would like to remove compound assignments to be crystal clear there is no alteration of the value in place (there should be another operator for this). Of course repeating left hand side of the assignment (with possible subexpressions) is a nasty thing to do. Unless ³:

msg = "world";
msg = "hello " + $;

On the expense of little more typing user will get way more power — I think it is a fair exchange.


¹ What is the motivation for Scala assignment evaluating to Unit. It seems Scala was supposed to evaluate assignments to their left hand side value, not right.

² What was the reason for Swift assignment evaluation to void — do you know the answer?

³ The idea is not mine (as usual), but I cannot recall where did I read this, I will update this post as soon as I find out.

Tagged , , , , ,

The object initialization

Writing constructors by hand is so tedious that I am happy C# has object initializers. Well, sort of happy, because they are not really object initializers (they are just member assignments) and because of that they often collide with the configuration of the members (private or readonly). One thing I cannot deny — they offer really compact form of setting up the object:

new Point() { X = 5.3, Y = 7.2 };

Scala and Kotlin address the same problem providing also compact form, true initialization, however in not very pleasing manner:

class Point(var x: Double, 
            var y: Double) 
{
  ...
}

Without such constructor the structure of type definition is pretty clear, with constructor added all of the sudden part of the type is moved as parameters, so it looks like a method which is, and which is not at the same time. Different taste I assume.

Let’s write bare type Point in Skila:

class Point
  var x = Double(13.2);
  var y Double;
end

Some things worth noting — both fields are private by default, you cannot omit the typename unless you initialize the field (or property) with constructor, which is the case here. Type inference is useful feature to have but it is best served in moderate ratios.

Our Point type has default constructor, but we cannot initialize Point object with custom values. Let’s change it:

class Point
  in var x = Double(13.2);
  in var y Double;
end

And that’s it — the keyword in says ”add named parameter to constructor and initialize the given field with it”. In other words such constructor is added behind the scenes:

  def init(x : Double = 13.2, y : Double)
    this.x = x;
    this.y = y;
  end

Because of the named parameters (note the colon) the compiler can add default values wherever it wants. Named parameters also mean user has to provide the names:

Point(x : 3, y : 15.5);
Point(y : 7, x : 1); // the order does not matter
Point(y : 1.5);
Point(2, 3.5); // error, no names
Point(x : 2); // error, missing `y` parameter

What can I say — I honestly like this design. It is as clear as C# code, but you don’t lose any benefit of real constructor. What’s more, you can use in keyword as a parameter and an argument as well:

base class Animal
  in let weight Double;
end

class Human : Animal
  in let iq Double;
  let label String;

  def init(label String = "Joe", in)
    super(in); // calling base constructor
    this.label = label;
  end
end

// `label` is anonymous parameter
Human("Jane",iq:130,weight:60); 

The only requirement is in parameter has to come last, it is small price to pay if you ask me.

Tagged , , , , ,

Leaving the trenches of the Option<T> type

Please note currently Skila has only reference types (not that it is well thought over decision, I simply don’t have enough time to deal with value types).

The problem how to return data from the function efficiently while fitting in special “no result” value, haunts me for some time. I am aware of several approaches:

  1. magic values, like -1 for indices (it is still used, see Go),
  2. thin Nullable<T> type to mark there is no result (you can see this in Kotlin),
  3. rich Option<T> type for wrapping the actual value (Swift, Scala approach),
  4. Try-Parse pattern (for sure it is used in C# libraries).

The first approach is dead simple and fast, yet it is disaster when it comes to serious programming — each time you have to check what magic value you can get. The second approach is much better but it does not scale very well — you can use it for a substring lookup, but it fails with dictionary getter or such functions as first on collection. Yet, the performance is on par with magic values.

For me the only realistic answers are the last two — with Option<T> type you can work with any function, you just add an extra layer of Option<T> to the working type. The performance suffers but you always have fast counterpart functions tryDoSomething. Of course some poor soul has to write all those pairs of functions now — because of that I was seriously considering supporting two types at the same time, lightweight Nullable<T> and rich Option<T>.

Oh yes, there is another approach:

  1. communicate failure (like in Icon),

I have no idea what the performance is, but the Icon code is simply beautiful. It was about time to read a book about it — I barely even opened The Implementation of the Icon Programming Language by Ralph E. Griswold and Madge T. Griswold when I found this inspiring passage:

(…) the design of programming languages should not be overly inhibited by perceived implementation problems, since new implementation techniques often can be devised to solve such problems effectively and efficiently.

I am sold — I want beauty, and I want performance! Nothing less. I want stackable (nested) Option<T> type, easy to use with speed of raw null values. Until now I was focusing on optimizing nested Option<T> type, but maybe I could somehow add a stack to null… wait a second.

Let’s consider what happens on the first nesting level (think of Option<T>) — we have either the actual value or a null. On the second level (Option<Option<T>>) — the actual value or a null again. At both levels when we have the actual value we can recognize that we didn’t end up with no result because our reference is not equal to null. It is the null which has to be wrapped (because null from the first level of nesting plays a role of true data on the second level), the real, actual value does not need any wrapping. It is some progress but we still have to do a little wrapping, right? No, we don’t — just turn the microscope on and take a look. In the first case the failure is indicated by null¹, in the second case by another, different nullnull².

Click, click, click — do you hear this sound?

Option<T> type. Who said it is a regular type in the first place? It does not have to be — our Option<Option<T>> is a disjoint union of types. It is Null² type, or Null¹ type, or T type — Null²|Null¹|T.

Because we have to tell compiler what type we would like to get, it knows at what level it operates — i.e. how many layers it should pretend unwrapping to get the value. If it is any of the null value cases, it will also know how long it should pretend it has real data — the show with single null keyword is just for the user. Say the pointer is set to null¹ and our current type is Option<Option<String>> — do we have real value? Sure thing, it is not null² and that’s all we have to care about.

Thanks to all those lies there is no wrapping values in the runtime, the speed is the same as working with plain old null values. The only difference comparing to rich Option<T> school is with down casting — we will be able to tell what type we hold in hand (String for example), but we will not be able to deduce what union of types it comes from (Null¹|String or maybe Null²|Null¹|String).

Could it be this cookie is absolutely for free? Unfortunately — no. Union types does not work well with generic types (at least if you want to keep static control over types), but since we have here very specific case of union we can enrich type info with option counter. Whenever there is Option<T> type used we have to take option counter from type T and increment it.

This leaves me a syntax to think about and supporting three valued logic to consider — this could add an interesting twist to the language.

Tagged , , , , , , , , , , , , ,

Nulls are OK

Judging by the hot disputes about null it should be some kind of the problem, but I have to admit I don’t see any. A lot of people complain about getting NullPointerException (and alike) as a bad thing — for me it is great. It is the mechanism that stops my program and tells me “listen, the flow of your program is incorrect, I prevented bad things to happen, sit down and fix it”. I am grateful for that because I didn’t add any extra line to my program and yet the runtime keeps me safe. null values are very useful if you start to treat them as normal citizens among your data, same way as you treat zeros when doing computations.

a = b + c;

Are you sweating because “b” could be zero?

Some languages try to cover null “problem” by introducing wrapper class for reference/pointer types (for example Scala with its Option ¹). However what kind of progress here is made with actually renaming null to None? I don’t see any ².

Since C# and extension methods I see things differently — to such extent that I started writing extensions instead of regular methods just to allow null on the caller side (to this day I remember pride of C++ which guarantees “this” cannot be null).

In many cases you have to deal manually with null, period, but in many, especially when the job is related to collections, null comes naturally. Consider such task — having HTML node extract first “<p>” node from its children, and then extract all “<span>” nodes from its children. If you use XPath query you have one sequence of selectors. How come in classic programming you have to add so many guards against null? Why not solve this without fear of null?

var spans = ((node??emptyNode)
              .Children
              .Where(it => it.Name=="p")
              .FirstOrDefault()??emptyNode)
                .Children
                .Where(it => it.Name=="span");

The only problem, or rather annoyance, is C# — not null.

Kotlin addresses the issue directly but misses the point — instead of introducing coalesce operator it allows subsequent call/access to fail (Kotlin “returns” null):

var children = node?.Children;

If “node” is null, the variable ”children” will be null as well (Fantom and Groovy also took this approach). I am not saying coalesce is superior in all cases, but adding a feature which moves you from null domain into the same null domain does not look like a solution to me.

Skila will use selective Null Object pattern ³ with short coalesce operator. For every type you can define a constant null object for coalescing. And then…

var spans = node->Children
            .Where(it => it.Name=="p")
            .FirstOrDefault()->Children
            .Where(it => it.Name=="span");

spans” won’t be null! Arrow operator (“->”) is hidden coalesce call. Because Skila is statically typed checked, it verifies at compile time whether you can use the power of coalescing (it checks if the null object is defined). And it does the right thing — it moves you from null domain into not-null domain.

This is probably not a complete blueprint — practice will be the best judge — but even upon completion it won’t be a magical wand. If you work on types that are collections, adding coalesce is like adding a grease into the gears, in other cases you should rely on old “if”, and for the rest — NPE comes to the rescue.


¹ I say ”yes” to Option, but not instead of null pointers, but as addition to them.

² Why Scala’s “Option” and Haskell’s “Maybe” types won’t save you from null (good read, but the example with Dictionary is weak).

³ There might a be a little confusion what the true “Null Object” pattern is, so let’s say Kotlin, Fantom, Groovy use thin null object (no body, everything falls into nulls), while Skila will use fat objects, with real body defined by user. This will allow to transform null collections into empty ones.

Tagged , , , , , , , ,

Modern constructor — how does it look?

For sure the way the constructors are written in C++ has to go — starting from naming constructor not by a name of the class, but simply “__construct” (like in PHP) or “init” (I would also like to add ability to return a value, but it is a minor thing as well). The real problem is how to initialize object fields in a constructor — briefly, yet in informative way?

Scala integrated constructor went too far — the code is very concise, true, but at the expense of the readability. Entire body of a class becomes a constructor and this means constructor parameters are leaking directly into all class methods.

C# is much better in this regard, I love its syntax:

new Person()
  {
    FirstName = "Joe",
    LastName = "Doe"
  };

The problem? It is not a constructor really (just the first line is). It is not only the matter of the name though, there are technical implications as well — “FirstName” and “LastName” cannot be readonly properties for example. But the clarity is hard to beat.

So the question for Skila is really this — how to bring C# syntax and make it real constructor? So far I came up only with an idea of macro constructor…

Mark the fields of the class which can be initialized by simple assignment and call constructor as usual — all parameters for marked fields are passed via magical “ini” tuple and initialized in one assignment.

class Foo
  var FirstName <- String("John");
  var LastName <- String;
  var BirthYear Int;

  def init(birthYear Int, $ini)
  do
    this.BirthYear = birthYear;
    this.$ini = $ini;
  end
end

new Foo(1918, FirstName : "Joe",
              LastName : "Doe");

Some of the features of macro constructor:

  • field pseudo-initialization serves as indication of optional argument, i.e. you could omit “FirstName” here when creating “Foo” object; it is not field initilization like in C#
  • when passing arguments via “ini” you have to name all arguments — in other words “ini” expands to a list of forced named parameters, and thanks to that it can always be safely placed as the last (pseudo) parameter,
  • because assignment in constructor is explicit you can decide when to call it.

Is this the best what can be done in 2013? Do you have better ideas?

Tagged , , , , ,