No, you cannot initialize a variable of one isolate from a different isolate. They don't have shared memory as you alluded to. The only method of communication between isolates is through ports.
Even though the analyzer may allow to you to modify a variable in one isolate from another, you won't get the behavior you expect. Isolates can be thought of as entirely different processes.
I've made an example to show this behavior:
import 'dart:isolate';
Future<void> main(List<String> arguments) async {
final single = Singleton();
print(single.variable);
single.variable = 1;
print(single.variable);
final port = ReceivePort();
final isolate = await Isolate.spawn(isolateWork, port.sendPort);
await for(dynamic message in port) {
if(message == 'done') {
isolate.kill();
break;
}
}
}
void isolateWork(SendPort port) {
final single = Singleton();
print('In isolate: ${single.variable}');
port.send('done');
}
class Singleton {
int variable = 0;
static final Singleton _singleton = Singleton._internal();
factory Singleton() {
return _singleton;
}
Singleton._internal();
}
This is a simple program that attempts to use a singleton to modify a variable in one isolate from a spawned one. If there were shared memory, one might expect the following output as I first obtain the singleton, print the default variable
value of 0
, change variable
to 1
, and then print variable
in the isolate:
0
1
In isolate: 1
However, since these isolates are completely separate processes, the spawned isolate has its own instance of the singleton, leading to the following output:
0
1
In isolate: 0
0
and 1
are printed as expected in the main isolate, but the spawned one has its own memory and uses a separate singleton object, so it prints 0
even though it's 1
in the main isolate.
As you can see in my example above, I did use ports so that my program could detect when the isolate was finished and gracefully kill the process. Passing messages with ports are the proper and only method of passing data between with isolates.
You tagged this question as flutter, so I'm guessing you're using Flutter. If you're doing a single, large computation with a single output, using Flutter's compute
method is probably the easiest way to use isolates as it removes the need for you to work with ports. However, it can be limiting and it's often useful to use a full isolate implementation like I did above.