How to Make Your Code Clean With Kotlin Sealed Classes

Поділитися
Вставка
  • Опубліковано 23 лип 2024
  • In this video you will learn how you can make your code cleaner using Kotlin sealed classes.
    ⭐ Get certificates for your future job
    ⭐ Save countless hours of time
    ⭐ 100% money back guarantee for 30 days
    ⭐ Become a professional Android developer now:
    pl-coding.com/premium-courses...
    💻 Let me personally review your code and provide individual feedback, so it won't backfire and cost you a fortune in future:
    elopage.com/s/philipplackner/...
    Subscribe to my newsletter for regular Android, Kotlin & Architecture advice!
    pl-coding.com/newsletter
    Join this channel to get access to perks:
    / @philipplackner
    Regular live codings on Twitch:
    / philipplackner
    Join my Discord server:
    / discord
    Regular programming advice on my Instagram page: / _philipplackner_
    Checkout my GitHub: github.com/philipplackner
    You like my free content? Here you can buy me a coffee:
    www.buymeacoffee.com/philippl...
    00:00 - Introduction
    00:18 - Sealed classes vs. enum classes
    07:23 - Using sealed classes to handle responses
    10:41 - Exposing state in a ViewModel
    14:58 - Making your code more readable

КОМЕНТАРІ • 110

  • @francismwangi9752
    @francismwangi9752 Рік тому +5

    I was really struggling to understand sealed classes, but now I can even explain to someone else after watching the video. Thanks Phillip

  • @petejewel
    @petejewel 2 роки тому +56

    Enum classes limit instantiation. Sealed classes limit inheritance.

    • @bjugdbjk
      @bjugdbjk 2 роки тому

      Most importantly enums have a larger footprint, Avoid as much as we can instead use annotations (typedef int) !!

    • @user-tx4rq5sy1t
      @user-tx4rq5sy1t 2 роки тому +2

      @@bjugdbjk that’s not true any more, i would advice you to look into ART (Android runtime) vs DVM

  • @jatinvashisht4293
    @jatinvashisht4293 2 роки тому +21

    OMG, you made the video on topic I requested in one of your recent videos.
    Thank You Philipp 😊

  • @AmitJayant
    @AmitJayant Рік тому +2

    16:50 "I don't know, there are so many now a days" 😂😂

  • @bjugdbjk
    @bjugdbjk 2 роки тому

    tysm !! I was looking for the best tutorial for sealed classes and here it goes :) !! u r bringing smiles to android dev's crazy life !! Thanks a ton, buddy !!

  • @user-hp2yi9yy3x
    @user-hp2yi9yy3x 2 роки тому +2

    I just today wanted to learn about sealed classes and here you are.

  • @chrisfelix9065
    @chrisfelix9065 2 роки тому +2

    I am always happy to be welcomed back to your new video 🤓

  • @keepgoingman5829
    @keepgoingman5829 2 роки тому +1

    I always wait for your new videos. thank you so much. i love it!

  • @mustafaammar551
    @mustafaammar551 2 роки тому

    Very cool video
    I don't use sealed classes usually put after this video i will use it more
    Thank you Bro
    I wish you all the best

  • @kahanbhalani3607
    @kahanbhalani3607 2 роки тому

    Very well explained!

  • @sooshil
    @sooshil 2 роки тому

    I was not using them because I was not understanding them clearly. And, that is over now. Thanks Phil.... :)

  • @samuelgibson780
    @samuelgibson780 2 роки тому

    Thanks for this! After watching this video I realized I had written several classes using enums that would be better off as sealed classes. It's a huge improvement.

  • @juancaos01
    @juancaos01 2 роки тому

  • @BlueIsLeet
    @BlueIsLeet 9 місяців тому +1

    8:49 you're wild for that LOL

  • @otaviosgoncalves
    @otaviosgoncalves 2 роки тому

    Excelent explanation! Good job!

  • @venkatesh4307
    @venkatesh4307 2 роки тому

    I thought that I knew the use of sealed class. But it went wrong after this video 🤭🤭
    Thank you Philipp

  • @Sumitmaurya070
    @Sumitmaurya070 2 роки тому

    thankx philip , super

  • @bro_chenzox
    @bro_chenzox 2 роки тому

    Thank you!

  • @lukalukovic5082
    @lukalukovic5082 2 роки тому

    Really good videos Philipp

  • @nizamuddinahmed9165
    @nizamuddinahmed9165 2 роки тому

    Bravo! learnt something unexpected

  • @saumilpatel2480
    @saumilpatel2480 2 роки тому

    Legend!

  • @hcaltay
    @hcaltay 2 роки тому +1

    hey philipp, thanks for this video, i have a question, can we use interface instead of sealed class and if we can't why?

  • @pradeep9222
    @pradeep9222 2 роки тому

    hi Philipp, thank you the nice tutorial, I'm struggling with BaseActivity, BaseFragment, BaseViewModel and Almost every thing with prefix Base, Struggling to understand and write code in internship for my organization, 🙏 please make a video to clear this Base Prefix.

  • @mohammedelamin1563
    @mohammedelamin1563 2 роки тому

    Dude you saved me 😍

  • @pentexnyx5883
    @pentexnyx5883 2 роки тому +2

    I use it to listen to distinguish between Loading, Success and Failure states using when via collecting the flow as State :)

  • @user-ok3xn3vx3h
    @user-ok3xn3vx3h 2 роки тому +2

    Philip, thank you for the lessons! Please answer, is it possible to include subtitles with translation into other languages in the videos on your paid courses? On UA-cam, I watch them exactly like this:)

    • @PhilippLackner
      @PhilippLackner  2 роки тому +1

      Having auto-generated subtitles on Vimeo is incredibly expensive sadly

  • @bboydarknesz
    @bboydarknesz 2 роки тому +3

    thanks. but when get data from API to data class response, how can the field knows which object sealed class to use?
    for example, json response { name: 'Khalifa', gender: 'male' } with our sealed class Gender { Male, Female }
    is it automatically serialize base the object name?

    • @debjyotinath2986
      @debjyotinath2986 2 роки тому +2

      I have the same doubt. Philip could you please explain this?

  • @elijahonduso
    @elijahonduso 2 роки тому

    Haven't watched yet but I already know it's a thumbs up

  • @ubersticks
    @ubersticks 2 роки тому +3

    What is the thought for naming the Success/Fail data wrapper "Resource"? I see this similar technique with the same name (Resource) in other blogs and tutorials. "Result" seems a more intuitive name - but I see that Kotlin already has a built-in type class called "Result" with a very similar structure as the "Resource" code. Why not use the built-in Result and why name this Resource?

    • @dakopyc
      @dakopyc 11 місяців тому +1

      I had the same thought/question :) though perhaps Phillipp was adding this (new) class for the sake of the example? (and "Resource" kinda also makes sense... in HTTP parlance... i.e. "get/post/put/delete a resource"? :))

  • @abdremo
    @abdremo 2 роки тому

    thanks fleep

  • @algierm2329
    @algierm2329 2 роки тому

    What if there are multiple error type at the same time (e.g network error & input empty) to be displayed on ui? should i add it into variable in uistate data class only without Error sealed class or my question just too dumb to be asked? ^^

  • @pauloCosteira
    @pauloCosteira 2 роки тому +1

    Hey, talk about sealed class vs sealed interface

  • @KalpeshChari
    @KalpeshChari 8 місяців тому

    so There will be one uiState Class for each Activity?

  • @vengateshm2122
    @vengateshm2122 2 роки тому

    Kindly explain about in and out keywords in kotlin.

  • @allvideo4534
    @allvideo4534 2 роки тому

    Sir what is extension funcation?

  • @alinawaz9197
    @alinawaz9197 2 роки тому

    Hey Phillip! one of your biggest fans, Ali from Pakistan here..
    Can you please make a video on how do you debug network requests.
    Like in most of your videos you tell us how to get error or success responses easily from a request but what if I want to look at request body how can I do that with this Resource sealed class design pattern..
    Thanks in advance bro 💓

  • @TheMassif
    @TheMassif 2 роки тому +1

    Why are you not using polymorphism to render the UI elements if the state has an error? Basically, you could replace the “when” statement with a function in the specific UiState.Error and make it even easier to read

    • @mikec4220
      @mikec4220 2 роки тому

      Can you give an example?

  • @mahdizareei4575
    @mahdizareei4575 2 роки тому

    Thanks my friend, this video was awesome,
    but why you used that names for the person list?
    do you like them?
    XD

  • @michaelleffert9129
    @michaelleffert9129 2 роки тому +5

    No one's going to mention the names he's returning in the person service?

  • @kamertonaudiophileplayer847
    @kamertonaudiophileplayer847 2 роки тому +3

    The general problem of teaching to a language capability nowadays is providing a cookbook approach. I will show you how to use sealed classes. Oh, cool. Imagine we have a car class and... Okay, why do not show it in a different way. Show class of problems sealed classes can help you to solve.

  • @damercy
    @damercy 2 роки тому +1

    Am I the only one who saw Mia Khalifa in the list of persons at 8:58? xD On a serious note, thank you for these content Phillip. :)

  • @gauravthakkar802
    @gauravthakkar802 2 роки тому

    Hey Philip, why not use a single class to pass the resource from the repository to the viewmodel and to the view? Why do we have two different classes i.e. UiState and Resource

    • @gauravthakkar802
      @gauravthakkar802 2 роки тому

      Also we could have Error as an enum rather than a sealed class because we just simply want a countable list of stuff

    • @PhilippLackner
      @PhilippLackner  2 роки тому +5

      1. The resource class is responsible for carrying the result of the API response. The repository does not have the purpose of deciding what the UI sees. If you hardcode that into your repository, you can only use it with one view model and one screen.
      2. Enum works as well, but using a sealed class is better to distinguish between errors in a when expression because the compiler knows of all the options and won't complain that there is no else branch

    • @gauravthakkar802
      @gauravthakkar802 2 роки тому

      That's a brilliant insight my man. Also the first one, I think you didn't get my point, I was saying that you can have a same class across the Repository and Viewmodel to depict state. I mean I do it for my projects so what's the difference between having a UiState and Resource differently because both have to convey state right?

    • @NavinPrasad06
      @NavinPrasad06 2 роки тому

      @@gauravthakkar802 Can you provide your sample code here ? or share link of gist.

  • @SparshMr
    @SparshMr Рік тому

    Where do I get the source code for this tutorial?

  • @wavecycle
    @wavecycle 2 роки тому

    Great video thank you, it's much clearer now! One question though regarding the data on a Success:
    even though the "data" parameter for Success is non-nullable "T", it will still accept null as an input, and then down the line, in the "when" block where I'm checking for "is Resource.Success"... Then I need to follow it up with a check to see if the data is not null. Is there a way around? Thanks!!!
    when (trackResult) {
    is Resource.Success -> {
    if (trackResult.data == null || trackResult.data.component1() == null)
    throw IllegalStateException("Resource.Success should not have null data")
    val trackInfo = JSONObject(
    String(trackResult.data.component1()!!)
    )
    track = trackInfo.createTrackFromJson()
    }
    is Resource.Error -> {}
    }

    • @PhilippLackner
      @PhilippLackner  2 роки тому +1

      you could by making changing the data of the success resource to a val and renaming it, but then you have two datas which is kinda confusing

    • @neil2444
      @neil2444 2 роки тому

      If I recall correctly, he doesn't use a question mark to allow null values in case of success, compared to Resource.Error which does optionally take data that is nullable. In other words, there will never be a null value in case of success because you simply could not create an instance of Resource.Success with a null value. Of course if you wanted that, you could always change it so that it could accept null values (but I think an empty list is better than null).

    • @user-dv7te5xf8m
      @user-dv7te5xf8m 2 роки тому

      In Google testing repo I finded next code. Mayby this helpig out.
      sealed class Result {
      data class Success(val data: T) : Result()
      data class Error(val exception: Exception) : Result()
      object Loading : Result()
      override fun toString(): String {
      return when (this) {
      is Success -> "Success[data=$data]"
      is Error -> "Error[exception=$exception]"
      Loading -> "Loading"
      }
      }
      }
      val Result.succeeded
      get() = this is Result.Success && data != null
      // useed
      data for class Result will available only in next block code
      if (usersResult is Success) {
      saveInDatabase(usersResult.data)
      }

  • @phatho3875
    @phatho3875 2 роки тому

    Why do we need a constructor in Resource sealed class while we can declare variables in those sub-classes?

    • @PhilippLackner
      @PhilippLackner  2 роки тому +1

      when you don't know yet what type of resource a specific resource is, you can access its data/message. That doesn't work if you only put that in the subclass constructors

    • @leonardopaixao3785
      @leonardopaixao3785 2 роки тому +1

      ​@@PhilippLackner if you define an constructor in sealed class, every child has to define this attribute.
      for instance, if you know that each element of sealed class has an specific attribute, you don't neet to check if an object is of a specific type to access his attribute.
      sealed class Job(name: String){
      object Guardian : Job("guardian")
      object Cop: Job("cop")
      }
      imagine that you have an list of elements of Job, and you want to render the name of each one. You can do it like this:
      listOf(Job.Cop, Job.Guardian).forEach{ job ->
      println(job.name)
      }
      now imagine that the attributes belongs for each child of Job.
      sealed class Job{
      data class Guardian(name: String) : Job()
      data class Cop(name: String): Job()
      }
      To print the name of each one, you ll need to verify the type to assure that the current object is an specific type, to access his attribute.
      listOf(Job.Guardian("guardian"), Job.Cop("cop")).forEach{ job ->
      when(job){
      is Cop -> println(job.name)
      is Guardian -> println(job.name)
      }

  • @dakopyc
    @dakopyc 11 місяців тому

    Thanks as always for the video, Philipp. However, you didn't really explain exactly what (and why/when) sealed classes are used; as compared to regular classes or enums. Apparently, they are "sealed from extension" -- though I've never really understood why this is considered a "good thing". :) Perhaps you could cover/explain that in a followup video?

    • @SprinkzMC
      @SprinkzMC 7 місяців тому +1

      "sealed from extension" means that a sealed class like Car only has the possible subclasses (like Audi, Bmw, Mercedes) defined by you in your files. other people or files cannot make their own cars: the class is sealed.
      this is good because it allows the compiler to know that the subclasses it sees are the only ones that exist. for example, if you have a function taking a Car, you can use the when(){} operator and handle Audi, Bmw, and Mercedes only -- there's no need for an unecessary "else ->" branch, like there would be with regular classes, because with a sealed class kotlin knows exactly what type of cars exist, while with a regular class someone could make their own type of Car and call your function with it.
      enums and sealed classes/interfaces are similar: they are both useful for declaring possible "states" a value could have. for example, a DayOfWeek enum/sealed class would contain monday, tuesday, wednesday, etc. -- enums and sealed classes would both be suitable for making DayOfWeek.
      however, say you wanted a Vowel enum/sealed class, containing A, E, I, O, and U as possible states. for this to be useful, you might also want to store each vowel's character value, so you can easily make functions that can easily access the character of a Vowel passed into them. this is what enum classes are useful for:
      enum class Vowel(val character: Char) {
      A('A')
      }
      above, A('A') is a shorthand for A = Vowel('A'): in an enum, states are all instances of the enum class. therefore, Vowel.A is an instance of Vowel and Vowel.A.character is 'A'. keep in mind that every enum instance is of the exact same type, in this case Vowel. it wouldn't be possible to create a Vowel called Y and give it an isAlwaysVowel value of false without giving an isAlwaysVowel values to A, E, I, O, and U too. for this example, regular enums make sense.
      but imagine you wanted a good way to represent the result of a divide(a: Double, b: Double) function that returns a/b. this seems simple until you remember that you cant divide by zero... so then what? if b is 0 should you just throw an error? with sealed interfaces you can avoid this. think in terms of states. the possible result of the divide() function can have either a success or error state. if the result is a success, it should also have a number associated with it.
      it's not possible to do this with a regular enum, because with enums you can't say "vowel A should have some character associated with it" -- you can only say "vowel A should have 'A' associated with it". enum states are constants, not types. but in a sealed class/interface, the possible states are classes. for example, you could make a sealed class DivisionResult with states of Success and DivideByZeroError. the error is a singleton and Success is a class that has a num attribute.
      sealed interface DivisionResult {
      class Success(val num: Double) : DivisionResult
      object DivideByZeroError : DivisionResult
      }
      these both inherit from DivisionResult, and since DivisionResult is sealed, the compiler knows that a variable of type DivisionResult is always going to be either a DivideByZeroError or a Success (with a number associated). say you have "val x = DivisionResult.Success(1.1)". here, x is an instance of DivisionResult.Success, which inherits from DivisionResult. x.num is 1.1.
      the best way to think about the difference between enums and sealed classes is that an enum is really a collection of constants with values pre-assigned, while a sealed class heirarchy is a collection of types with their own shapes and values.

  • @codewithroman8180
    @codewithroman8180 2 роки тому

    Continuous jet pack compose playlists

  • @nesibeyyubov554
    @nesibeyyubov554 2 роки тому +1

    At 17:00 , why to use sealed classes instead of enum class? i mean Gender class could be enum like:
    enum class Gender{ Male, Female }

    • @PhilippLackner
      @PhilippLackner  2 роки тому +4

      With sealed classes when-expressions are nicer because they remind you when you're missing a class in the when expression. But yea, enum classes work as well, I just like sealed classes more as I said in the video

  • @GoodGuyFinishFirst
    @GoodGuyFinishFirst 2 роки тому +3

    But why not to use enum in example with Gender? It should be more concise.

  • @rushlive
    @rushlive 2 роки тому +5

    that Moment i saw a person name of "Mia Khalifa"

  • @sandersaelmans1401
    @sandersaelmans1401 2 роки тому

    Have you considered using sealed interfaces instead?

    • @neil2444
      @neil2444 2 роки тому

      Not sure how useful sealed interfaces would be if ultimately you must also create a sealed class that uses it, and you would have to with this particular usage. Could still be useful for other applications I'm sure.

  • @maddman9171
    @maddman9171 2 роки тому +1

    Dude, the little easter eggs are so funny! Mia Khalifa ^^

  • @mohegyux4072
    @mohegyux4072 Рік тому +1

    8:50 Mia khalifa 😂😂

  • @shahhussain1448
    @shahhussain1448 2 роки тому

  • @k4ba
    @k4ba Рік тому +1

    Mia Khalifa and a multi gender talk in the same video.
    You are wild bro haha
    As always great content

  • @demianbel
    @demianbel 2 роки тому +1

    Great video and thank you for the explanation of sealed class. It's not clear for me as an web-developer (maybe it's android specific) why we don't use emum instead of sealed class in all these examples. These classes don't have any logic inside so how it would be better than enum. And the second point, as I know switch with type check can be replaced with method like getMessage in the sealed class and implementation of it in each type of error. In this case I don't see a reason to make it sealed and close this hierarchy for extension hence every error has to implement this method and will work without main activity changes.

    • @iliasg
      @iliasg 2 роки тому +1

      The use of enum classes in Android is discouraged as it mostly requires twice as much memory, which is limited in Android. The usage of sealed classes allows to write more future-proof code as each subclass can have their own implementations while an enum class will have to define the same variables and functions for each enum constant. Whenever you need an additional single function, you don't have to define it everywhere with sealed classes. An enum class exists as an object which means it can only have a single instance when you use values, while a sealed class allows multiple with their own state. For the when statement, you mostly want to keep the specific implementation outside of the sealed class to make it reusable and allow a different implementation based on where you need the class. If you need a variable in all subclasses, you can still define it in the sealed class constructor itself. Extending sealed classes defies its purpose as it represents a restricted hierarchy known at compile-time. Using a when statement for this allows you to use the classes without casting them.

  • @ajaykori3014
    @ajaykori3014 2 роки тому +1

    16:52 talking about tiktok guys nowadays they are on the instagram cool 😂🤣

  • @DeLL116
    @DeLL116 2 роки тому

    Thank you for this 🙇‍♂️🙇‍♂️🙇‍♂️
    Can you say in your next video..."Jennifer poops at parties?" 🤪😉😘

  • @francoisloriot2674
    @francoisloriot2674 2 роки тому

    just for info, Kotlin is not an Android only language, and sealed classes exist in java as well.

    • @PhilippLackner
      @PhilippLackner  2 роки тому

      For Android, java does not support sealed classes

    • @francoisloriot2674
      @francoisloriot2674 2 роки тому

      @@PhilippLackner insteresting. isn't java supposed to be Write Once Run Anywhere?

  • @justinxu8205
    @justinxu8205 Рік тому +1

    bro put mia khalifa in at 8:49 😭

  • @lBOSS6
    @lBOSS6 2 роки тому

    Philipp? Is it really the right repository in description? There is no sealed class.

    • @PhilippLackner
      @PhilippLackner  2 роки тому +1

      Oh thanks for telling me it was wrong. I don't have a repository for this video

  • @valcron-1000
    @valcron-1000 2 роки тому

    These are called "Sum types", part of "Algebraic Data Types". By the way, your "Resource" type looks a lot like the "Either" type

  • @MaisUmSomente
    @MaisUmSomente 2 роки тому

    Very good, it has not to be a BOOLEAN to be a BOOLEAN.

  • @suaranitizen6832
    @suaranitizen6832 2 роки тому

    how to fix this Warning: Mapping new ns thanks sir

  • @baderkhaneoussama
    @baderkhaneoussama 2 роки тому

    Is it only me who spotted “Mia khlifa “ name at 08:46. 😂

  • @sahuadarsh0
    @sahuadarsh0 2 роки тому

    Enum class on steroids 🤣

  • @elijahonduso
    @elijahonduso 2 роки тому +1

    Thought I was the first one..

    • @IUfidi
      @IUfidi 2 роки тому

      Appy coding!

  • @-ECE-SOGATAKAR
    @-ECE-SOGATAKAR 5 місяців тому

    you are very handsome your content is also amazing

  • @Berk45632
    @Berk45632 2 роки тому

    Sir sir. Who is Mia Khalifa??🤣

  • @fsfaysalcse
    @fsfaysalcse 2 роки тому

    Mia Khalifa 😅 What an example bro 😛

  • @MsArmen1998
    @MsArmen1998 2 роки тому

    mia khalifa

  • @argahutama
    @argahutama Рік тому

    Mia Khalifa 😆

  • @heavenlife5619
    @heavenlife5619 2 роки тому +1

    *As a java android developer i see Kotlin is worst language with weird syntax and weird new things*

    • @PhilippLackner
      @PhilippLackner  2 роки тому +3

      As tetris Player I see call of duty as worst game with weird graphics and weird new things

    • @heavenlife5619
      @heavenlife5619 2 роки тому +1

      @@PhilippLackner *You look like henry cavill*

  • @jopanovyigod
    @jopanovyigod 2 роки тому

    This is just bad

  • @Chekist2008
    @Chekist2008 2 роки тому

    Thank you!