Home > Mobile >  Concurrency in kotlin also block after synchronized block
Concurrency in kotlin also block after synchronized block

Time:07-13

I have a block of code like this in kotlin.

synchronized(this) {
   // do some work and produces a String
}.also { /*it: String*/
   logger.log(it)
}

can some thread come and with unlucky timing the it variable gets changed before logging happens? (There are a lot of threads executing this piece of code concurrently)

CodePudding user response:

To expand on comments:

  1. The synchronized block returns a reference that's passed into the also block as it; that reference is local to the thread, and so there's no possibility of it being affected by other threads.

  2. In general, there's no guarantee about the object that that reference points to: if other threads have a reference to it, they could potentially change its state (or that of other objects it refers to).

    But in this case, it's a String; and in Kotlin, Strings are completely immutable. So there's no risk of that here.

Taking those together: the logging in OP's code is indeed thread-safe!

However:

  1. We can't tell whether there could be race conditions or other concurrency issues within the synchronized block, before the String gets created and returned. It synchronizes on this, which prevents two threads simultaneously executing it on the same object; but if there are two instances of the class, each one could have a single thread running it.

    So for example there could be an issue if the block uses some common object that's not completely thread-safe, or some instance property that's set to the same reference in both instances, or if there's sharing in a more roundabout way. Obviously, this will depend upon the nature of the work done in that block, what objects it accesses, and what it does with them. So that's worth bearing in mind too.
  • Related