{"id":681,"date":"2017-11-10T18:18:02","date_gmt":"2017-11-10T18:18:02","guid":{"rendered":"https:\/\/devexperts.com\/blog\/?p=681"},"modified":"2022-05-18T10:53:43","modified_gmt":"2022-05-18T10:53:43","slug":"kotlin-from-the-trenches","status":"publish","type":"post","link":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/","title":{"rendered":"Kotlin From The Trenches"},"content":{"rendered":"\n<p>In the last few years, the growth of hype around the Kotlin programming language has been about the same as that of the Bitcoin rate. This close attention was gingered up even more in May 2017, when Google declared official support of Kotlin for the development for Android. Of course, we couldn\u2019t help joining the study of this topic and decided to experiment with Kotlin, using it in our new Android-based project.<\/p>\n\n\n\n<p>Kotlin is a statically typed programming language that runs on top of the JVM; it is developed by JetBrains. Kotlin combines the principles of an object-oriented and functional programming language. According to the developers, it is pragmatic, concise, and interoperable. Applications written in it can be run on the JVM or compiled in JavaScript, and the native compilation support is around the corner. It is important to note that the language was created simultaneously with the development tools and fine-tuned to be used with them.<\/p>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\"><p>By now, many articles have been dedicated to Kotlin and many reports on it have been made. We\u2019ll try to focus not so much on the distinctive features of the language, praising it or scolding it, as on our practical experience of benefiting from its features.<\/p><\/blockquote>\n\n\n\n<p>So, let\u2019s contemplate each of the mentioned aspects\u2026<\/p>\n\n\n\n<h2 id=\"h-the-best-tooling\" class=\"wp-block-heading\">The best tooling<\/h2>\n\n\n\n<p>The developer of the Kotlin language is JetBrains, a software development company that has produced probably the best IDE for Java and many other programming languages. Despite all the verbosity of the Java language, the writing speed remains very high: the environment &#8220;writes the code&#8221; for you.<\/p>\n\n\n\n<p>With Kotlin, there is a feeling that you have purchased a new keyboard and still cannot get used to it and you aren\u2019t able to touch-type despite trying. IntelliSense often just doesn\u2019t keep up with the speed of typing; where IDE will generate a whole class for Java, for Kotlin you are going to be looking at the progress bar. And the problem is not only with new files: navigating actively through the project may result in IDE freezing so only restarting it will help you.<\/p>\n\n\n\n<p>It&#8217;s upsetting that many of the tricks you&#8217;re used to just stop working. For example, Live Templates. Android Studio \u2013 (a version of IntelliJ IDEA for Android development) &#8211; comes with a set of convenient templates for frequently used operations, such as logging. The logm + Tab combination will insert a code that will record a message to the log about which method with which parameters has been called:<\/p>\n\n\n<pre><code class='codeBlock bash'><\/p>\n<p>Log.d(TAG, 'method() called with: param = [' + param + = ']');<\/p>\n<p><\/code><\/pre>\n\n\n\n<p>In doing so, this template &#8220;knows how&#8221; to correctly determine the method and parameters, depending on where you applied it.<\/p>\n\n\n\n<p>However, it does not work in Kotlin. Moreover, you\u2019ll have to create a separate template (for example, klogd + Tab) and use it based on the programming language. The reason why the 100% IDE-compatible languages require managing settings twice, remains a mystery to us.<\/p>\n\n\n\n<h2 id=\"h-is-it-easy-to-learn\" class=\"wp-block-heading\">Is it easy to learn?<\/h2>\n\n\n\n<p>Kotlin, despite the possibility of compiling into JavaScript and potentially into the native code (using Kotlin.Native), is primarily a language for JVM and its purpose is to spare Java developers the unnecessary and potentially dangerous (prone to bugs) boilerplate. However, it is a mistake to assume that writing in Kotlin from the very start will actually be Kotlin at all. To draw an analogy with languages, at first you\u2019ll be writing in &#8220;Spanglish&#8221; with a strong Java accent. We saw this when reviewing our own code after some time, as well as when observing the code of colleagues who were just beginning to learn the language. This manifested the most in working with null and nonNull types, as well as in the excessive &#8220;verbosity&#8221; of expressions, a habit that\u2019s hard to kick. In addition, the huge number of new features, e.g., extension methods open Pandora&#8217;s Box for writing black magic spells, adding excessive complexity where it wasn\u2019t called for, and making the code more confusing and hard to review. A telling example is the invoke () method overloading, which allows masking its call under a constructor call so that visually creating a Dog type object, you can get pretty much anything:<\/p>\n\n\n<pre><code class='codeBlock kotlin'><\/p>\n<p>class Dog private constructor() {<br \/>\n    companion object {<br \/>\n        operator fun invoke(): String = 'MAGIC'<br \/>\n    }<br \/>\n}<\/p>\n<p>object DogPrinter {<br \/>\n    @JvmStatic<br \/>\n    fun main(args: ArrayString) {<br \/>\n        println(Dog()) \/\/ MAGIC<br \/>\n    }<br \/>\n}<\/p>\n<p><\/code><\/pre>\n\n\n\n<p class=\"Textbody\">Thus, despite it won\u2019t take you more than a week to master the syntax, it may take several months to learn to correctly apply the features of the language. In some cases, a more detailed study of the principles of the operation of certain syntactic sugar, including the study of the obtained bytecode, will be necessary. When using Java, you can always refer to such sources as <a href=\"https:\/\/www.amazon.com\/Effective-Java-2nd-Joshua-Bloch\/dp\/0321356683\">Effective Java<\/a> to avoid many troubles. Even though Kotlin was designed to eliminate &#8220;troubles&#8221; brought by Java, &#8220;troubles&#8221; brought by Kotlin are yet to be revealed.<\/p>\n\n\n\n<h2 id=\"h-null-safety\" class=\"Textbody wp-block-heading\">Null safety<\/h2>\n\n\n\n<p class=\"Textbody\">The Kotlin language has a sophisticated type system. It allows you, in most cases, to avoid the most popular problem in Java &#8211; NullPointerException. Each type has two options, based on whether a variable of this type can be null. If you can assign null to a variable, the question mark is added to the type. Example:<\/p>\n\n\n<pre><code class='codeBlock kotlin'><\/p>\n<p>val nullable: String? = null<\/p>\n<p>val notNull: String = ''<\/p>\n<p><\/code><\/pre>\n\n\n\n<p>Nullable variable methods are called using the .? operator. If such method is called on a variable that is null, the result of the entire expression will also be null; however, the method will not be called and NullPointerException will not occur. Of course, the developers of the language left a way to call the method on a nullable variable, no matter what, and get a NullPointerException. To do this, instead of ? you will have to write !!:<\/p>\n\n\n<pre><code class='codeBlock kotlin'><\/p>\n<p>nullable!!.subSequence(start, end)<\/p>\n<p><\/code><\/pre>\n\n\n\n<p>This line is jarring and the code loses its neatness. Two consecutive exclamation &nbsp;are likely to indicate that such a code was deliberately written. On the other hand, it is difficult to think of a situation where using the !! operator would be necessary.<\/p>\n\n\n\n<p>Everything looks good until the entire code is written in Kotlin. If, however, Kotlin is used in an existing Java-based project, everything becomes much more complicated. The compiler is unable to track which variables will be null, so to determine the type correctly is next to impossible. For variables from Java, null tests are not available at compile time. The developer will thus take the responsibility of choosing the right type. Besides, in order for the automatic conversion from Java to Kotlin to work correctly, the code in Java must contain @Nullable\/@Nonnull annotations.<\/p>\n\n\n\n<p>If, however, a null finds its way from the Java code into Kotlin, a crash with the exception of the following kind is inevitable:<\/p>\n\n\n<pre><code class='codeBlock java'><\/p>\n<p>FATAL EXCEPTION: main<\/p>\n<p>Process: com.devexperts.dxmobile.global, PID: 16773<\/p>\n<p>java.lang.RuntimeException: Unable to start activity ComponentInfo{com.devexperts.dxmobile.global\/com.devexperts.dxmarket.client.ui.generic.activity.GlbSideNavigationActivity}: java.lang.IllegalArgumentException: Parameter specified as non-null is null: method kotlin.jvm.internal.Intrinsics.checkParameterIsNotNull, parameter savedInstanceState<\/p>\n<p><\/code><\/pre>\n\n\n\n<p>Having disassembled the bytecode, we can find the spot from which the exception was thrown:<\/p>\n\n\n<pre><code class='codeBlock bash'><\/p>\n<p>ALOAD 1<br \/>\nLDC \"param\"<br \/>\nINVOKESTATIC kotlin\/jvm\/internal\/Intrinsics.checkParameterIsNotNull(Ljava\/lang\/Object;Ljava\/lang\/String;)V<\/p>\n<p><\/code><\/pre>\n\n\n\n<p>The deal is that for all parameters of non-private methods, the compiler adds a special check: the standard library method is called<\/p>\n\n\n<pre><code class='codeBlock bash'><br \/>\nkotlin.jvm.internal.Intrinsics.checkParameterIsNotNull(param, \"param\")<br \/>\n<\/code><\/pre>\n\n\n\n<p>If necessary, you can disable it by using the compiler directive<\/p>\n\n\n<pre><code class='codeBlock bash'><br \/>\n-Xno-param-assertions<br \/>\n<\/code><\/pre>\n\n\n\n<p>This directive should be reserved for extreme cases as it only gives a slight increase in performance at the expense of the likely loss of reliability.<\/p>\n\n\n\n<p>To all classes that have the get () method, you can use the [] operator in Kotlin. It is very convenient. For example:<\/p>\n\n\n<pre><code class='codeBlock kotlin'><br \/>\nval str = 'my string'<br \/>\nval ch = str[2]<br \/>\n<\/code><\/pre>\n\n\n\n<p class=\"Textbody\">However, the index access operator can only be used with non-null types. A nullable version does not exist, and in a case like that you will have to explicitly call the get () method:<\/p>\n\n\n<pre><code class='codeBlock kotlin'><br \/>\nvar str: String? = null<br \/>\nval ch = str?.get(2)<br \/>\n<\/code><\/pre>\n\n\n\n<h2 id=\"h-properties\" class=\"wp-block-heading\">Properties<\/h2>\n\n\n\n<p class=\"Textbody\">Kotlin makes it easier to work with class fields. You can access fields as normal variables, and a getter or a setter of the desired field will be called.<\/p>\n\n\n<pre><code class='codeBlock java'><br \/>\n\/\/ Java code<br \/>\npublic class IndicationViewController extends ViewController {<br \/>\nprivate IndicationHelper indicationHelper;<br \/>\nprotected IndicationHelper getIndicationHelper() {<br \/>\nreturn indicationHelper;<br \/>\n}<br \/>\n}<br \/>\n<\/code><\/pre>\n\n\n<pre><code class='codeBlock kotlin'><\/p>\n<p>\/\/ Kotlin code<\/p>\n<p>val indicationViewController = IndicationViewController()<\/p>\n<p>val indicationHelper = indicationViewController.indicationHelper<\/p>\n<p><\/code><\/pre>\n\n\n\n<p class=\"Textbody\">Things get complicated if you need to override a Java class getter in a Kotlin class. At the first glance, it seems that indicationHelper is a full-fledged property compatible with Kotlin. As a matter of fact, this is not so. If we try overriding it &#8220;head-on&#8221;, we\u2019ll most definitely get a compilation error:<\/p>\n\n\n<pre><code class='codeBlock kotlin'><\/p>\n<p>class GlobalAccountInfoViewController(context: Context) : IndicationViewController(context) {<br \/>\nprotected open val indicationHelper = IndicationHelper(context, this)<br \/>\n}<\/p>\n<p><\/code><\/pre>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/kotlin-example.png\"><img loading=\"lazy\" decoding=\"async\" width=\"701\" height=\"121\" src=\"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/kotlin-example.png\" alt=\"\" class=\"wp-image-693\" srcset=\"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/kotlin-example.png 701w, https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/kotlin-example-300x52.png 300w\" sizes=\"auto, (max-width: 959px) calc(100vw - 30px), 870px\" \/><\/a><\/figure>\n\n\n\n<p>All is done correctly: declared in the subclass is a property whose getter has a signature absolutely identical to the superclass getter. What is wrong then? The compiler takes care of us, suggesting that the overriding happened by mistake. There is even a discussion on this subject in the <a href=\"https:\/\/discuss.kotlinlang.org\/t\/how-to-implement-getter\/388\">Kotlin forum<\/a>. There we can learn two important things:<\/p>\n\n\n\n<ol class=\"wp-block-list\"><li>\u201cJava getters are not seen as property accessors from Kotlin\u201d<\/li><li>\u201cThis may be enhanced in the future, though\u201d<\/li><\/ol>\n\n\n\n<p>And it seems that there\u2019s only one correct way to achieve our goal (also from the forum): to create a private variable and at the same time override the getter.<\/p>\n\n\n<pre><code class='codeBlock kotlin'><br \/>\nclass GlobalAccountInfoViewController(context: Context) : IndicationViewController(context) {<br \/>\nprivate val indicationHelper = IndicationHelper(context, this)<br \/>\noverride fun getIndicationHelper() = indicationHelper<br \/>\n}<br \/>\n<\/code><\/pre>\n\n\n\n<h2 id=\"h-100-javainterop\" class=\"wp-block-heading\">100% Java-interop<\/h2>\n\n\n\n<p>Perhaps we should have placed this paragraph first, because it was Java-interop that allowed the new language to gain such popularity so quickly that even Google declared official support of the language for the development for Android. Unfortunately, we did not avoid surprises here either.<\/p>\n\n\n\n<p>Let\u2019s consider a simple thing known to all Java developers: access modifiers or visibility modifiers. In Java, there are four of them: public, private, protected, and package-private. Package-private is used by default, unless you specify otherwise. In Kotlin, the modifier used by default is public, and it (like both the protected and the private) is called and works exactly as in Java. However, the package-private modifier in Kotlin is called \u201cinternal\u201d and it works somewhat differently.<\/p>\n\n\n\n<p>The language designers wanted to address the problem with the potential ability to disrupt encapsulation when applying the package-private modifier. The solution was to create a package in the client code with the same name as in both the library code and the method pre-defining. Such trick is often used when writing unit-tests in order not to open &#8220;to the outside&#8221; the method created for testing purposes. This is how the internal modifier appeared, which makes the object visible inside the module.<\/p>\n\n\n\n<p>The name module applies to the following:<\/p>\n\n\n\n<ul class=\"wp-block-list\"><li>Module in the IntelliJ Idea project<\/li><li>Project in Maven<\/li><li>Source set in Gradle<\/li><li>A set of source codes compiled with a single ant-script launch<\/li><\/ul>\n\n\n\n<p>The problem is that internal is actually public final. Thus, when compiling at the bytecode level, you can accidentally override a method that you did not want to override. Because of this, the compiler will rename your method so that such a thing does not happen, which in turn will make it impossible to call this method from Java code. Even if the file with this code is in the same module, in the same package.<\/p>\n\n\n<pre><code class='codeBlock kotlin'><br \/>\nclass SomeClass {<br \/>\ninternal fun someMethod() {<br \/>\nprintln('')<br \/>\n}<br \/>\n}<\/p>\n<p>public final someMethod$production_sources_for_module_test()V<br \/>\n<\/code><\/pre>\n\n\n\n<p>You can compile your Kotlin code with the internal modifier and add it as a dependency to your Java project. In this case, you can call this method where the protected modifier would not allow you to do so, i.e., you will get access to the private API outside of the package (because the method is de facto public), although you will not be able to override. One may get the feeling that the internal modifier was not designed as part of the &#8220;Pragmatic Language&#8221;, but rather as a feature of the IDE. And such behavior could have been made by using annotations, for example\u044e despite many statements that very few keywords are reserved in Kotlin, for example, for coroutines, internal actually chains your Kotlin-based project to the JetBrains IDE. If you are developing a complex project that consists of a large number of modules and some of these modules may be used as dependencies by colleagues in a pure Java-based project, think carefully before writing common parts in Kotlin.<\/p>\n\n\n\n<h2 id=\"h-data-classes\" class=\"wp-block-heading\">Data Classes<\/h2>\n\n\n\n<p>The next, probably one of the most famous features of the language, is data classes. Data classes allow you to quickly and easily write POJO-objects, equals, hashCode, toString and other methods for which the compiler will write for you.<\/p>\n\n\n\n<p>This is really a handy thing, however, beware of traps in compatibility with libraries used in the project. In one of our projects, we used Jackson to serialize\/deserialize JSON. When we decided to rewrite some POJOs in Kotlin, it turned out that the Jackson annotations did not work correctly with Kotlin and it was necessary to additionally connect a separate jackson-module-kotlin for compatibility.<\/p>\n\n\n\n<h2 id=\"h-in-conclusion\" class=\"wp-block-heading\">In conclusion<\/h2>\n\n\n\n<p>Even though this article may come off as criticizing, we do like Kotlin! Especially on Android, where Java got stuck on version 1.6, it became a true salvation. We understand that Kotlin.Native, coroutines and other new features of the language are very important and correct things, but they just may not be useful to everyone. At the same time, the IDE support is what each developer uses, and the slow work of the IDE negates all the speed benefits we get switching to Kotlin from the verbose Java. While the decision to switch to Kotlin or to stay on Java for the time being, is to be taken by each individual team, all we want is to share the problems that we had to face, which will hopefully save you precious time.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>In the last few years, the growth of hype around the Kotlin programming language has been about the same as &hellip; <\/p>\n","protected":false},"author":39,"featured_media":1609,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[2020],"tags":[36,60],"class_list":["post-681","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-fintech","tag-development","tag-kotlin"],"acf":{"nifty_post_card_image":null,"nifty_post_card_index_big":null,"nifty_post_inner_image":null,"nifty_post_card_banner":null},"yoast_head":"<!-- This site is optimized with the Yoast SEO Premium plugin v27.2 (Yoast SEO v27.2) - https:\/\/yoast.com\/product\/yoast-seo-premium-wordpress\/ -->\n<title>Kotlin Programming From The Trenches \u2013 Devexperts Blog<\/title>\n<meta name=\"description\" content=\"We experiment with Kotlin programming language in our Android-based project and show how it helps solve existing Java difficulties.\" \/>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/\" \/>\n<meta property=\"og:locale\" content=\"en_US\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"Kotlin From The Trenches\" \/>\n<meta property=\"og:description\" content=\"We experiment with Kotlin programming language in our Android-based project and show how it helps solve existing Java difficulties.\" \/>\n<meta property=\"og:url\" content=\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/\" \/>\n<meta property=\"og:site_name\" content=\"Devexperts Blog\" \/>\n<meta property=\"article:publisher\" content=\"https:\/\/www.facebook.com\/devexperts\/\" \/>\n<meta property=\"article:published_time\" content=\"2017-11-10T18:18:02+00:00\" \/>\n<meta property=\"article:modified_time\" content=\"2022-05-18T10:53:43+00:00\" \/>\n<meta property=\"og:image\" content=\"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/cian-full.png\" \/>\n\t<meta property=\"og:image:width\" content=\"3840\" \/>\n\t<meta property=\"og:image:height\" content=\"700\" \/>\n\t<meta property=\"og:image:type\" content=\"image\/png\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:creator\" content=\"@devexperts\" \/>\n<meta name=\"twitter:site\" content=\"@devexperts\" \/>\n<meta name=\"twitter:label1\" content=\"Est. reading time\" \/>\n\t<meta name=\"twitter:data1\" content=\"12 minutes\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\/\/schema.org\",\"@graph\":[{\"@type\":[\"Article\",\"BlogPosting\"],\"@id\":\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#article\",\"isPartOf\":{\"@id\":\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/\"},\"headline\":\"Kotlin From The Trenches\",\"datePublished\":\"2017-11-10T18:18:02+00:00\",\"dateModified\":\"2022-05-18T10:53:43+00:00\",\"mainEntityOfPage\":{\"@id\":\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/\"},\"wordCount\":2383,\"commentCount\":0,\"publisher\":{\"@id\":\"https:\/\/devexperts.com\/blog\/#organization\"},\"image\":{\"@id\":\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#primaryimage\"},\"thumbnailUrl\":\"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/cian-full.png\",\"keywords\":[\"development\",\"kotlin\"],\"articleSection\":[\"Fintech\"],\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"CommentAction\",\"name\":\"Comment\",\"target\":[\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#respond\"]}]},{\"@type\":\"WebPage\",\"@id\":\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/\",\"url\":\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/\",\"name\":\"Kotlin Programming From The Trenches \u2013 Devexperts Blog\",\"isPartOf\":{\"@id\":\"https:\/\/devexperts.com\/blog\/#website\"},\"primaryImageOfPage\":{\"@id\":\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#primaryimage\"},\"image\":{\"@id\":\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#primaryimage\"},\"thumbnailUrl\":\"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/cian-full.png\",\"datePublished\":\"2017-11-10T18:18:02+00:00\",\"dateModified\":\"2022-05-18T10:53:43+00:00\",\"description\":\"We experiment with Kotlin programming language in our Android-based project and show how it helps solve existing Java difficulties.\",\"breadcrumb\":{\"@id\":\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#breadcrumb\"},\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/\"]}]},{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#primaryimage\",\"url\":\"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/cian-full.png\",\"contentUrl\":\"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/cian-full.png\",\"width\":3840,\"height\":700},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\/\/devexperts.com\/blog\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"Kotlin From The Trenches\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\/\/devexperts.com\/blog\/#website\",\"url\":\"https:\/\/devexperts.com\/blog\/\",\"name\":\"Devexperts Blog\",\"description\":\"We make complex finance ideas on technology, innovation and business simple\",\"publisher\":{\"@id\":\"https:\/\/devexperts.com\/blog\/#organization\"},\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\/\/devexperts.com\/blog\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-US\"},{\"@type\":\"Organization\",\"@id\":\"https:\/\/devexperts.com\/blog\/#organization\",\"name\":\"Devexperts LLC\",\"url\":\"https:\/\/devexperts.com\/blog\/\",\"logo\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\/\/devexperts.com\/blog\/#\/schema\/logo\/image\/\",\"url\":\"https:\/\/devexperts.com\/blog\/app\/uploads\/2019\/08\/DX-logo.png\",\"contentUrl\":\"https:\/\/devexperts.com\/blog\/app\/uploads\/2019\/08\/DX-logo.png\",\"width\":167,\"height\":30,\"caption\":\"Devexperts LLC\"},\"image\":{\"@id\":\"https:\/\/devexperts.com\/blog\/#\/schema\/logo\/image\/\"},\"sameAs\":[\"https:\/\/www.facebook.com\/devexperts\/\",\"https:\/\/x.com\/devexperts\",\"https:\/\/www.linkedin.com\/company\/devexperts\",\"https:\/\/www.youtube.com\/channel\/UCF3FRmes2KrcVsTXQ1aAB5w\/featured\"]}]}<\/script>\n<!-- \/ Yoast SEO Premium plugin. -->","yoast_head_json":{"title":"Kotlin Programming From The Trenches \u2013 Devexperts Blog","description":"We experiment with Kotlin programming language in our Android-based project and show how it helps solve existing Java difficulties.","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/","og_locale":"en_US","og_type":"article","og_title":"Kotlin From The Trenches","og_description":"We experiment with Kotlin programming language in our Android-based project and show how it helps solve existing Java difficulties.","og_url":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/","og_site_name":"Devexperts Blog","article_publisher":"https:\/\/www.facebook.com\/devexperts\/","article_published_time":"2017-11-10T18:18:02+00:00","article_modified_time":"2022-05-18T10:53:43+00:00","og_image":[{"width":3840,"height":700,"url":"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/cian-full.png","type":"image\/png"}],"twitter_card":"summary_large_image","twitter_creator":"@devexperts","twitter_site":"@devexperts","twitter_misc":{"Est. reading time":"12 minutes"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":["Article","BlogPosting"],"@id":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#article","isPartOf":{"@id":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/"},"headline":"Kotlin From The Trenches","datePublished":"2017-11-10T18:18:02+00:00","dateModified":"2022-05-18T10:53:43+00:00","mainEntityOfPage":{"@id":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/"},"wordCount":2383,"commentCount":0,"publisher":{"@id":"https:\/\/devexperts.com\/blog\/#organization"},"image":{"@id":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#primaryimage"},"thumbnailUrl":"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/cian-full.png","keywords":["development","kotlin"],"articleSection":["Fintech"],"inLanguage":"en-US","potentialAction":[{"@type":"CommentAction","name":"Comment","target":["https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#respond"]}]},{"@type":"WebPage","@id":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/","url":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/","name":"Kotlin Programming From The Trenches \u2013 Devexperts Blog","isPartOf":{"@id":"https:\/\/devexperts.com\/blog\/#website"},"primaryImageOfPage":{"@id":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#primaryimage"},"image":{"@id":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#primaryimage"},"thumbnailUrl":"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/cian-full.png","datePublished":"2017-11-10T18:18:02+00:00","dateModified":"2022-05-18T10:53:43+00:00","description":"We experiment with Kotlin programming language in our Android-based project and show how it helps solve existing Java difficulties.","breadcrumb":{"@id":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#breadcrumb"},"inLanguage":"en-US","potentialAction":[{"@type":"ReadAction","target":["https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/"]}]},{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#primaryimage","url":"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/cian-full.png","contentUrl":"https:\/\/devexperts.com\/blog\/app\/uploads\/2017\/11\/cian-full.png","width":3840,"height":700},{"@type":"BreadcrumbList","@id":"https:\/\/devexperts.com\/blog\/kotlin-from-the-trenches\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/devexperts.com\/blog\/"},{"@type":"ListItem","position":2,"name":"Kotlin From The Trenches"}]},{"@type":"WebSite","@id":"https:\/\/devexperts.com\/blog\/#website","url":"https:\/\/devexperts.com\/blog\/","name":"Devexperts Blog","description":"We make complex finance ideas on technology, innovation and business simple","publisher":{"@id":"https:\/\/devexperts.com\/blog\/#organization"},"potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/devexperts.com\/blog\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-US"},{"@type":"Organization","@id":"https:\/\/devexperts.com\/blog\/#organization","name":"Devexperts LLC","url":"https:\/\/devexperts.com\/blog\/","logo":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/devexperts.com\/blog\/#\/schema\/logo\/image\/","url":"https:\/\/devexperts.com\/blog\/app\/uploads\/2019\/08\/DX-logo.png","contentUrl":"https:\/\/devexperts.com\/blog\/app\/uploads\/2019\/08\/DX-logo.png","width":167,"height":30,"caption":"Devexperts LLC"},"image":{"@id":"https:\/\/devexperts.com\/blog\/#\/schema\/logo\/image\/"},"sameAs":["https:\/\/www.facebook.com\/devexperts\/","https:\/\/x.com\/devexperts","https:\/\/www.linkedin.com\/company\/devexperts","https:\/\/www.youtube.com\/channel\/UCF3FRmes2KrcVsTXQ1aAB5w\/featured"]}]}},"_links":{"self":[{"href":"https:\/\/devexperts.com\/blog\/wp-json\/wp\/v2\/posts\/681","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/devexperts.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/devexperts.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/devexperts.com\/blog\/wp-json\/wp\/v2\/users\/39"}],"replies":[{"embeddable":true,"href":"https:\/\/devexperts.com\/blog\/wp-json\/wp\/v2\/comments?post=681"}],"version-history":[{"count":34,"href":"https:\/\/devexperts.com\/blog\/wp-json\/wp\/v2\/posts\/681\/revisions"}],"predecessor-version":[{"id":2058,"href":"https:\/\/devexperts.com\/blog\/wp-json\/wp\/v2\/posts\/681\/revisions\/2058"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/devexperts.com\/blog\/wp-json\/wp\/v2\/media\/1609"}],"wp:attachment":[{"href":"https:\/\/devexperts.com\/blog\/wp-json\/wp\/v2\/media?parent=681"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/devexperts.com\/blog\/wp-json\/wp\/v2\/categories?post=681"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/devexperts.com\/blog\/wp-json\/wp\/v2\/tags?post=681"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}