Kotlin Flows in a Nutshell

Video Statistics and Information

Video
Captions Word Cloud
Reddit Comments
Captions
hey guys welcome back to new video in this video i will quickly explain you flows in kotlin so i'm sure you've heard of them they are basically live did on steroids so very similar to livedata but they can even do a little bit more and they are entirely based on curitins so you should be familiar with curitins if you're watching this video here i have a very detailed playlist about that so if you don't know these then just watch that playlist first and then you're good to go then you can follow through this video here so i'm in an empty android studio project here and i also made sure to include these curtin dependencies here i'll include these in this video's description so you can quickly add these to your project um and in main activity i will just show you some basic flow stuff here so with plain crew routines when we have suspend function here for example um let's call it hello world whatever that returns something so let's say a string here then we could simply return that string in that function and when we return that string that function is over so we return out of that function of course flows actually take that concept to the next level because in the flow we can return several values at different times so we don't have that return statement instead what it is called for flows is we can emit a value so when using flows we have a producer and a consumer so the p producer actually emits new values and the consumer well consumes them does something with these values so what could that actually be useful for for example i am currently working on a little drawing game that uses web sockets so with web sockets we can just establish a continuous connection through server and both client and server can continuously send data to each other so for that i actually use a flow to just collect all these pieces of data that my server actually sends to my app and then i will process these pieces of data asynchronously in a flow and the cool thing here about flows is that they fully support back pressure so what is back pressure that is just um kind of a mechanism when the server actually sends more data at a given time than the client can process so you have to imagine that let's say you have a server that sends 20 000 pieces of data in a very short time and the client usually displays all that data in its ui then it can't really display that much data in a single second or so in its ui because that's just too much data so what flows will actually make sure or what this back pressure i talked about will actually make sure here is that the producer actually only gives data to the consumer when the consumer can process that so you will see here in this video how this works in detail but just that you're familiar with this um term back pressure another cool use case would be to cache network requests locally on an android device if you want to learn about that i showed that in detail in my caterer course on my website so just take a look at the first link in this video's description and with the discount code philip 15 you can get 15 off of that course so let's actually take a look here how this works in practice so we can actually create a flow object here valve flow and we can set that equal to flow you can see we have that lambda function here we want to choose that and each flow must be of a specific type so that will be the type of object we actually emit in that flow so let's say we want to emit strings so for example the string hello world then in here you can see we have access to this emit function and this emit function now takes this value that we specified here and we'll lead that to the producer or to the consumer sorry um we haven't specified that consumer yet but you will see how that works let's do follow up here for i in 1 to 10 we simply want to emit let's say the string hello world and you can already see that a suspend function here and that little icon so everything inside of this flow block will actually happen inside of a croutine so we can cut those pen functions here like delay for example so let's import that and delay that creatine for one second in each iteration of that for loop so it will basically emit the string hello world each second 10 times so now that is the producer as i said it produces values here it emits those and now we can specify the consumer that will actually well consume those and do something with these strings that it gets from this flow of course you wouldn't do it like this in practice with hello world that doesn't make much sense but this is just the easiest way to um show you how this producer and consumer mechanism here actually works with flows so in my example of that um of that drawing game where i use web sockets you just have to imagine that this flow comes from a library and this library calls emit with some kind of data that comes from my server and in the consumer i can then retrieve that data and simply do something with that and the consumer must actually be launched in a curtin so i will just use global scope here usually in an activity you should choose um lifecycle scope but i don't have that dependency right now so i'll just use globalscope for demonstration here and in here we can then call this flow dot collect so that collect function will actually give us these values that we emit in this flow here so in here we could simply use print line and simply print it so you can see it is actually that string and that we got from that flow so each second this producer flow will emit hello world and that means that this consumer flow will print hello world each second so let's actually run that app and try it out take a look here in logcat i'll filter that for hello world and you can see each second we get that string hello world here so that works as expected but what was that back pressure i actually talked about so let's say this consumer here actually needs more time to process that data well with this hello world string that is not an issue but if tons of data are coming in here actually and that consumer actually can't can't handle that at once then the producer will actually wait and buffer that data and then keep leading that data to the consumer when it is actually ready again to process that data so let's say this consumer is actually delayed for two seconds so it actually takes longer to consume than the producer needs to produce those values if we now run that again take a look at logcat here then you can see it's still in its values but now it is actually much slower and if we take a look at the timestamps here you can see it actually takes three seconds instead of two here so why is that we only delight the consumer here for two seconds but it actually only prints values every third second the reason for that is that by default this curtin here is the same creatine as this collect curtin here so that means that producer and consumer run in the same cruelty and of course if the producer then suspends that will also suspend the consumer and the other way around so if the consumer suspends here then this will also slow down the producer so for each emission here we actually lay the producer for one second and the consumer for two seconds so it can only print something in total of every third second so that is of course nothing we want if the client actually needs to do a lot of work and that two second delay here actually simulates that a lot of work here that the client needs to do um so you need to think about that this client just processes a big network request here and does a lot of stuff with that and that would of course also delay that producer here that actually delivers these network requests so how can we actually deal with that luckily with flows we have a super cool operator function which is called buffer so we can call that buffer here after the flow and that again returns a flow of string so we can just put that buffer here and that will just give us a default amount default buffer size here and it will actually execute the consumer in a different queue routine than the producer so if we now run that up again take a look in logcat now you can see hello world hello world this time you can see it's actually only a two second difference because this consumer here or actually this consumer here runs in a different routine than this producer because we include that buffer operator so that will just make sure that it gets all these values from the producer and buffers these so it saves these and when this consumer is actually ready again it will just redirect that to the consumer so you could optionally also pass any number here how big you want that buffer to be so that would just be a number in bytes i guess but that is important to know of course if you continuously get more data than your client can process and that doesn't really stop so the client can't keep up with that then that buffer will overflow at some point because at some point you just don't have any memory anymore so you really have to be aware of that and use this buffer operator here with caution and just really be sure that if a lot of data comes in then only that it comes in at once and not in a continuous stream so the client should be able to keep up with the data on average and one last thing i want to show in this video are actually those typical number functions you also know from lists like filter like map you also have these for flows so let's actually change this flow here remove this string and instead emit these integer values i here because we can i can just demonstrate that better with these values if we have integers here then we could simply also call dot filter for example and we need to import that here and that will give us a lambda function that you also know from lists so we can just pass a boolean expression here that describes which values we actually want to collect here so for example it modulo 2 equal to 0 we only want to collect values that are actually even numbers and then we could also use the map function for example that we also need to import here and for example map each value to its square so it times it and if we now rerun this take a look here in logcat and we'll see we get value 4 16 36 so we basically only get even values and then we get these even values squared so i'm sure you have heard of these map with filter functions from lists that is exact exactly the same here with flows so that we can just collect the results of these simple lambda functions here so of course this doesn't really make sense here but just that you have seen that that you actually have that option to transform whatever comes in in your consumer flow but that's actually it for flows there's a lot more to these which is actually more advanced but what you've learned in this video is actually 90 of what you will need most of the time so the rest is actually only stuff that you will look up if you need it it's similar to git but i actually never really need it more than what i showed you here in this video so if you like this video give it a like comment below and of course also make sure to subscribe to my channel if you haven't already have an awesome day see you next video bye bye [Music] [Music] you
Info
Channel: Philipp Lackner
Views: 25,122
Rating: 4.9822745 out of 5
Keywords: philipp, philip, phillip, phillipp, filip, filipp, philp, lackener, flows, flow, kotlin, coroutine, coroutines, android studio, networking, network request, asynchronous
Id: B_3iTVJT8Zs
Channel Id: undefined
Length: 13min 59sec (839 seconds)
Published: Fri Nov 06 2020
Related Videos
Note
Please note that this website is currently a work in progress! Lots of interesting data and statistics to come.