Kotlin / kotlinx.collections.immutable

Immutable persistent collections for Kotlin
Apache License 2.0
1.12k stars 56 forks source link

Giving Immutable Collections Shorter Names #14

Open GlenKPeterson opened 6 years ago

GlenKPeterson commented 6 years ago

Programmers are lazy. Immutable collections are safer than mutable ones. Therefore, they should have shorter names (less typing) than the mutable ones.

To this end I'd like to propose using "im" instead of "immutable" as a prefix for persistent/immutable collections and builders. imListOf() instead of immutableListOf() makes it shorter than mutableListOf(). Still not as short as listOf().

I attended a Josh Bloch (I'll try to find the link later) where someone asked him about his biggest regret with the design of Java and he said it was that common collections weren't built into the language. When I look at JSON in JavaScript, or the built-in collection syntax in Clojure, it's really sweet. Arguably one of the stronger aspects of both languages that you can so briefly define data right in code. To that end, I designed all my builders to just be 3 letters: vec(), set(), map(), and tup() for Vector, HashSet, HashMap, and Tuple2/3.

Kotlin has already used [] as a shortcut for getElementAt(), so we aren't getting Clojure/JavaScript -like syntax for immutable lists, and we're pretty much out of other symbols. But I thought I'd throw it out there that really brief syntax for creating immutable data structures is awesome. Especially if it's shorter than the syntax for creating mutable ones. So whether you use "f" for frozen, "im" for immutable, or "p" for persistent, or something else, I just wanted to advocate for not having to type out the 9-letter word, "immutable" every time I reach for my preferred collections.

Still, we could follow Clojure's example of using # to prefix another symbol, so that #[1 2 3] could be a persistent/immutable list of ints. #<1 2 3> might be a set. #("one" 1) a tuple. #{#("one" 1) #("two" 2)} a map. It's a thought. I put a lot of data structures in my code for little immutable things. I don't like brevity in general, but for something like this, it's really sweet.

ilya-g commented 6 years ago

I just wanted to advocate for not having to type out the 9-letter word, "immutable" every time I reach for my preferred collections.

Even if we settle on ImmutableList in the end, you won't have to type it every time. Just type ImList and the completion will do the rest for you.

stephenjfox commented 6 years ago

What if, instead, the names were the same as the current Collections:

kotlinx.collections.immutable.List is exactly what you think it should be, whereas List is what would be returned with listOf() (for example).

The imports (dis)ambiguate your code from the start, and the names are no longer than we're already used to. Further, the IntelliSense can give us ALT+ENTER choices for imports

cbruegg commented 6 years ago

Having to choose between two imports every time I use collection-related methods and classes sounds unconvenient, in my opinion.

Am Do., 5. Okt. 2017, 18:05 schrieb Stephen Fox notifications@github.com:

What if, instead, the names were the same as the current Collections:

kotlinx.collections.immutable.List is exactly what you think it should be, whereas List is what would be returned with listOf() (for example).

The imports (dis)ambiguate your code from the start, and the names are no longer than we're already used to. Further, the IntelliSense can give us ALT+ENTER choices for imports

— You are receiving this because you are subscribed to this thread. Reply to this email directly, view it on GitHub https://github.com/Kotlin/kotlinx.collections.immutable/issues/14#issuecomment-334512709, or mute the thread https://github.com/notifications/unsubscribe-auth/AAKtPezKEVYwJr3EVpmpteNZLqMDbFucks5spP4qgaJpZM4Ph4BY .

jcornaz commented 5 years ago

I would not bother too much about that. Users can create typealiases if they want shorter names in their code.

typealias ImList<E> = ImmutableList<E>
typealias ImCol<E> = ImmutableCollection<E>
typealias PList<E> = PersistentList<E>

But from the library point of view, it's better to make it as clear as possible.

Sporking commented 5 years ago

Common use of typealiases for commonly used standard classes are a problem. If different groups of people create different aliases, then people won't be able to read each other's code. Also, what do you do if more than one alias for the same type is imported from the libraries you import? This can easily become a mess.

Also, having more than one List class also sounds painful to me. Java made this mistake with java.util.List and java.awt.List, and it was a persistent annoying problem for code that had to use both in the same class. For commonly used classes, this is painful.

I would like to see shorter names. After using Guava and having to deal with multiple types with names like "ImmutableMultimap<String, ImmutableList\<Integer>>" in function declarations, I think that some shortening would be a good thing. Four syllables (9 characters) in "immutable" is a bit too many in my opinion. I would be in favor of a prefix ("Im") or just a shorter word to use as a prefix. Some candidates that occur to me: "Fixed", "Hard", "Frozen". I think "Frozen" is perhaps my favorite, since it carries the meaning pretty well, although "Hard" is even shorter and not bad either. There are lots of other options via https://www.thesaurus.com/browse/fixed,)

jcornaz commented 5 years ago

If different groups of people create different aliases, then people won't be able to read each other's code.

With any name it will become a mess if people use different types across the codebase. For instance some people could use the types from the kotlin standard library, some may use immutable collection from guava (could be in the classpath for another reason), and some other would use kotlinx.collections.immutable.

Like almost everything when many people work together on the same code, it has to be a team decision, and people have to use the same idoms and naming schemes.

Also, what do you do if more than one alias for the same type is imported from the libraries you import?

As often with typealiases, and even more on this cases it has to be internal. Libraries should not publish such aliases, but only use them internally. Users will just see the ImmutableList<E> declaration, even if a private alias has been used. It will always be self explanatory for the user of the library (no mater the name used in the lib implementation) and the user of the lib still has freedom to use his/her own aliases.

Also, having more than one List class also sounds painful to me. Java made this mistake with java.util.List and java.awt.List, and it was a persistent annoying problem for code that had to use both in the same class. For commonly used classes, this is painful.

Fully agree. They have to have different names.

Some candidates that occur to me: "Fixed", "Hard", "Frozen"

"Fixed" could be okay for me. But I really don't like "Hard" (what is a soft list?) and frozen is really not self-explanatory IMHO.

fvasco commented 5 years ago

Is FixedList a writable list with unmodifiable size, like the Array?

jcornaz commented 5 years ago

Is FixedList a writable list with unmodifiable size, like the Array?

no... It would be an immutable persistent list. But thanks for the pointing that Fixed is not a good naming either.