Java > Golang - How hard is it?

Java > Golang - How hard is it?

You'll be seeing more and more opportunities for Developers with Golang experience, but is the allure of the "dark side" enough to justify picking up a new language?


What is Go?

Go was designed at Google in 2007 in response to the challenges of Multicore, Networked machines and the demands of a large Codebase.

"Go is an open source programming language that makes it easy to build simple, reliable, and efficient software."

They wanted to combine the Static Typing & Runtime efficiency of C and the Readability and User-friendliness of Python.

The Go philosophy

You may have heard Java being called "the language of nouns".

Indeed, Java focuses on constructing types first, then defining the interaction between types. "What objects do I need, and how do they talk to each other?" After all, Object-Oriented Design (OOD) is an attempt to model software like the real world, where subjects receive input and act on it.

Go takes a different route. Go starts with the verb, the doing. "What action needs to be done?"

The primary building blocks in Go are functions. Yes, you can create types that have methods, but these do not need to be your starting point. Most packages of the Go standard library have top-level functions for immediate action.

This has a deep and wide impact on the design and implementation of libraries and executables. Most of the Gang Of Four (GoF) design patterns cannot be applied to Go unmodified or at all. Go also favours libraries as the standard building blocks of an application, rather than frameworks.


Interfaces

Interfaces in Go can be a source of confusion for Java developers. In Java, interfaces are predeclared and can contain a large number of functions.

In Go, an interface should be as small as possible. Interfaces with only one or two methods are not an exception but rather the rule. See also the Go proverb: "The bigger the interface, the weaker the abstraction".

And what's this thing about not being predeclared? This is indeed a fundamentally different way of interface usage. In a nutshell,

  • if a type implements all methods of an interface, it automatically implements that interface, no "implements" declaration is needed.
  • Thus, you can impose an interface over a third-party library's type, rather than having to rely on the library's author to define one. This is an insanely great way of, for example, swapping library types with your own mock types for testing.


Pointers

Go has pointers. This means you can take the address of any variable and pass that address around. Unlike C pointers, pointers in Go are safe, as they disallow any pointer arithmetic and are backed by the garbage collector.

Java has references, so the pointer concept is not entirely alien. But in Go, the concept is more explicit. By default, all function parameters are passed by value. If you create a struct (think "very simple Java class with fields and methods but without inheritance") and pass this struct to a function, the struct gets copied. In Java, an object created from a class is always passed as a reference. If you want to pass a variable by reference in Go, you need to tell the compiler to do so.


Public vs private

The visibility of functions, types, or fields is defined at the package level. There are no keywords like public or private. Instead, an identifier is public if its name starts with an uppercase letter. (This implies that identifier names must start with a Unicode character that has uppercase and lowercase variants. But that's just an aside.)


Compilation speed

This is perhaps one of the biggest productivity boosts in Go besides automatic memory management and a simple but effective language: Go code compiles insanely fast. Rather than requiring minutes to hours of build time, typical Go projects compile in seconds or minutes. And we are talking about compiling to native machine code.

Some aspects of Go do not exist in Java at all, or at least not in the core language. Here are a few examples.


Native concurrency

Concurrency in Go is built right into the language, no library needed. And the interface is simple as can be. The main ingredients are:

  • One keyword, go, to run a function concurrently. A function invoked this way is called a goroutine.
  • One primary communication mechanism, channels, to pass information between goroutines. (You can use mutexes and atomic types as well, but channels make it much easier to reason about your concurrent code.)

There is no management interface available for goroutines. No run, pause, stop, status, nothing. Goroutines are meant to be short-lived. Start one when a task is to be done, and have it finish its task as soon as possible.


Self-contained binaries

Not only do Go binaries need no virtual machine to run, they even do not need any dynamic libraries pre-installed on the system. No "DLL hell". A Go binary is always statically linked. You can compile it on machine A and run it on machine B without worrying about missing runtimes or libraries.

Java also has an option for compiling native binaries, even statically linked ones, by using GraalVM, an alternate JVM that can do ahead-of-time compilation. But believe me, it's more fun if that feature is right built into the core toolchain and is as easy as calling go build.


Native cross-compilation without a target toolchain

Pure Go code cross-compiles trivially. What does that mean? You can compile a Go binary for Linux on a Windows machine, without the need for installing a specific compiler toolchain for the target system. The same applied to different architectures and any combination of architecture and operating system. Does your build server run on Windows/i86 and your production servers on Linux/ARM? No problem.

And of course, the resulting binary needs no pre-installed libs or VM on the target system—see "self-contained binaries".


Functions are first-class citizens

Functions in Go can be used as variables and passed to or returned from functions. Look at this example from net/http that creates two functions h1 and h2 and passes them to http.HandleFunc to set up HTTP handlers for different endpoints. This is even possible for methods! Consider functions in Go like a generalization of Java's lambda expressions.


Inheritance

In Go, you can construct objects, but you cannot inherit behaviour from "parent" objects. This is not as limiting as it may seem. Go has mechanisms like interfaces and struct embedding that help compose new functionality from existing functionality. And remember that Go is verb-oriented. A well-designed library filled with functions and (flat) objects is a decent starting point for code reuse.


Method overloading

Go has no method overloading, and intentionally so. The lack of overloading makes code less confusing and fragile and also simplifies the type system.

Design decisions like this make Go code essentially non-magic. Go code clearly says what it does. What you see is what you get.


Exceptions

The Go designers deliberately omitted exceptions from the language. Error handling in Go is direct and explicit.

This forces developers to think about how their code can fail and provide useful error messages and context for each and every error that can possibly happen in the current function. Readers of the code immediately see where code can fail, and what it does in that case.

Agreed, the resulting code is much more verbose, and critics say that sometimes, the error handling code obscures the "happy path" of a function. But this is because non-fatal errors are part of a function's logic. (Go has a separate mechanism for fatal errors.) If a statement can error out, this fact should be visible in the code, right where the statement is called.


Interested in learning more? You can visit java2go.dev where you can learn more about Go from a Java developer's perspective.


Expanding your skills is always a great idea! - Lao Tzu believed that a journey of a thousand miles begins with a single step. 🤝 🌟 #Growth #Learning #Inspiration

Like
Reply

To view or add a comment, sign in

Insights from the community

Others also viewed

Explore topics