Properties in Kotlin


Properties in Kotlin ?

Properties are nothing but the variable with getter and setters, by Default kotlin provide the getter and setter for kotlin variables, So all the Kotlin variable are Properties.

In below example, name and age are variable, we should initialize these variables as they are non-nullable dataTypes.

I have declared them as var, so that we can change values. If I declare as Val then we cannot change the values of them.


class Person{
    var name:String = "chercher tech"
    var age:Int = 1 // year
}

Lets assign some value to the variables/properties in kotlin.


class Person{
    var name:String = "chercher tech"
    var age:Int = 1 // year
}
fun main(args: Array<String>) {
    var per = Person()
    // at zeroth month, my site name was selenium-webdriver.com
    // then I renamed it
    per.age = 0
    per.name = "selenium-webdriver.com"
    println(per.name)
    println(per.age)
}

Getters and setter in Kotlin :

Getters :

Getters are used to retrieve the value of the variable from the class, both val and var variable will have the getter

Setter :

Setters are used to set the value of the variables, only var variable has setter as we cannot change the value of val variable in kotlin.

In Kotlin, Getter an setter are automatically done by the kotlin compiler. Let's see how to add getter and setters manually in kotlin

Kotlin Compiler calls these getters and setters internally whenever you access or modify a property using the dot(.) operator on the class object.

Let's see the compiled code of the above program. Please do adjust with below image size.

To see decompiled code in your system, Navigate to Tools->Kotlin->Show Kotlin Byte Code and the select deCompile option but you might see the java code getters-setters-code-kotlin In above image you can see that getter and setter are only to help with getting and setting the value, but if we create our own getters and setters then we can write the code according to our needs.

Example for Getters and setter. In setter function, I have written my own code like println


class Person(age: Int) {
    val name: String = "chercher tech"
        get()=field
    var age: Int = age
        get() = field
        // set the value
        set(value) {
            println("Age value will be changed to : $age")
            field = value
        }
}
fun main(args: Array<String>) {
    // setting age
    var per = Person(13)
    println(per.name)
    println(per.age)
}

The major purpose of the getters and setter is get and set the value of a variable .

You might have noticed two identifiers in all the getter and setter methods - field and value. Lets talk about then now.

value :

We use value as the name of the setter parameter. This is the standard convention in Kotlin but you are free to use any other name if you want.

value identifier will be having the value that we are trying to assign to the variable.

In below example, I have change the identifier to some other name, does it sound familiar


class Person(age: Int) {
    val name: String = "chercher tech"
        get()=field
    var age: Int = age
        get() = field
        // using thanos instead of value identifier
        set(thanos) {
            println("Age value will be changed to : $age")
            field = thanos
        }
}
fun main(args: Array<<String>) {
    // setting age
    var per = Person(13)
    println(per.name)
    println(per.age)
}

Backing Field or field :

Backing field helps you refer to the property inside the getter and setter methods.

This is required because if you use the property directly inside the getter or setter then you’ll run into a recursive call which will generate a StackOverflowError.

Stack part of the RAM and it will be occupied completely because of the recursive call(recursive call is nothing but a function calling same function, Have you watched a movie called Triangle)


class Person() {
    var age: Int= 12 // initial value
        // set the value
        set(thanos) {
            age = thanos
        }
}
fun main(args: Array<String>) {
    // setting age
    var per = Person()
    println(per.age)
    // below assignment will make recursive calls
    // as we are performing setting operation
    per.age = 89
}

I have got below error message after printing the value as 12

Exception in thread "main" java.lang.StackOverflowError

Compile time constants (const) in kotlin :

Value of the variables that are know at compile time can be marked as compile time constants in kotlin using const keyword

  • Top-level of an object which means outside the main/any functions and outside any class
  • Initialized with a value of type String or a primitive type
  • No custom getter

A property with a custom getter can never be a compile-time constant. Kotlin does not support evaluating code at compile time.


const val age: String= "12"
fun main(args: Array<String>)
{
    println("age cost is : $age")
}

What is the Difference between val and const :

consts are compile time constants. Meaning that their value has to be assigned during compile time, unlike vals, where it can be done at runtime. This means, that consts can never be assigned to a function or any class constructor, but only to a String or primitive. For example:


const val foo = complexFunctionCall()   //Not okay
val fooVal = complexFunctionCall()  //Okay
const val bar = "Hello world"           //Also okay
fun complexFunctionCall(){
    // do something
}
fun main(args: Array<String>)
{
    println("age cost is : $age")
}

Any & Unit & Nothing

Kotlin Property/Variable Initialization

In Kotlin, when you define variable either we have to initialize with some value or define them in such way value can be null for those variables.

In some cases, you want to initialize the value later but don't want the variables to have the null value.

We can initialize the kotlin variables in different ways at different times of the execution of kotlin program, few methods are:

  • Lazy
  • LateInit
  • Delegates

Lazy initialization in Kotlin :

Sometimes variable are assigned with lazy Initialization, when you want that variable to get execute only once.

Lazy Initialization accepts a lambda and the lambda will be executed only once, when you call the variable again the lazy initialization will not be executed again but you will get the previous result.

Basically his results in singleton pattern kind of thing. For example, you have 10 page in your application, each one of the page requires a database connection, and also you have a logic and get the details of the database everyday for a per day token( so that you cannot store them in const as the token changes every day).

In this you might want to run the code to generate the token and use for the day, so do you think it is better to calculate that token (returns same token). 10 or 100 times, would thing to store the resut of first time execution in some place then use it for remaining times.

With lazy initialization you can achieve this.

In below example, I am println '****I have got executed*****' inside the lambda and returning nameAppend, but i am calling three time same var but it will execute the lambda only once that is first time


var nameAppend = "Kotlin"
// lazy works with lambda
val site: String by lazy {
    println("****I have got executed*****")
    // results KotlinKotlin for only first time
    nameAppend = nameAppend + nameAppend
    nameAppend
}
fun main(args: Array<String>)
{
    // I have called it three times
    println(site)
    println(site)
    println(site)
}

Lets create lambda and the val Lazy keyword and execute the above kotlin functions. You will get to know the difference


var nameAppend = "Kotlin"
// lazy works with lambda
val site: String by lazy{
    println("****I have got executed*****")
    // results KotlinKotlin for only first time
    nameAppend = nameAppend + nameAppend
    nameAppend
}
// normal lambda
val returnVauleLambda = {
    println("****I Am normal Lambda*****")
    // results KotlinKotlin for only first time
    nameAppend = nameAppend + nameAppend
    nameAppend
}
fun main(args: Array<String>)
{
    // call the lazy
    println(site)
    println(site)
    println(site)
    // call the lambda
    println(returnVauleLambda())
    println(returnVauleLambda())
    println(returnVauleLambda())
}

Nullability in Kotlin

Late Init in Kotlin :

In kotlin, you must initialize non-null variable while declaring, if you do not then compiler will show error for it.

But sometimes, you might do not want to initialize the variable, but you may want to initialize the variable, only before using it.

You should use the lateInit in case if you do not want to initialize a variable in while declaring.

LateInit initialization means you should be initializing the value for this variable before accessing it. In case we try to access the variable before initializing it we will see this error

Exception in thread "main" kotlin.UninitializedPropertyAccessException: lateinit property site has not been initialized

// if you note below line we have not initialize the 'site'
lateinit var site: String
fun main(args: Array<String>)
{
    site = "Chercher tech"
    println("Length of string is "+site.length)
}

Let's try without initializing the lateinit variable in kotlin


// if you note below line we have not initialize the 'site'
lateinit var site: String
fun main(args: Array<String>)
{
    println("Length of string is "+site.length)
}

Rues for LateInit :

  • LateInit should be applied with var property, val not allowed
  • LateInit can be applied on either a property inside the body of a class, or a top-level property
  • LateInit works only with non-null type
  • Does not not work with primitive types

Default Parameters

Delegates Observable in Kotlin :

Delegates.Observable makes sure that when a value changes of a particular variable, it can perform some actions like notifies you or it performs some changes. To use Delegates Observable you need to import a package from the kotlin language.

Basically it is something like a listener, it listens to the variable that we have declared with Delegates Observable.

You can provide the initial value for the Variable in Observable method as argument, Delegates Observable works with a lambda with three parameters, kotlin handles those parameters.

Delegates Observable can be applied only on var type not on val type variables in kotlin


import kotlin.properties.Delegates
// lazy works with lambda
var site: String by Delegates.observable("Selenium-mentor.com"){
    variableToObserver, oldValue, newValue ->
    // will be executed when there is change
    println("I was '$oldValue', but they changed me to '$newValue'")
}
fun main(args: Array%ltString>)
{
    site = "selenium-webdriver.com"
    site = "chercher.tech"
}

Operator Overloading in kotlin

aaaaaaaaaaaaa
Comment / Suggestion Section
Point our Mistakes and Post Your Suggestions

Recent Addition

new tutorial Selenium Online Training : Our next online training course for Selenium with Java starts from 17th December 2018.

You can attend first 3 classes for free, the total course fee is INR 10,000

The course time would be 8.00 PM(IST) for the first three classes

If you are interested to learn, then you can join the course by sending email to chercher.tech@gmail.com

or Register below


 
Join My Facebook Group
Join Group