Existe-t-il un moyen, supporté par le langage, de faire une copie complète (profonde) d'un objet dans Dart ?
Secondaire uniquement ; existe-t-il plusieurs façons de procéder, et quelles sont les différences ?
Merci pour la clarification !
Existe-t-il un moyen, supporté par le langage, de faire une copie complète (profonde) d'un objet dans Dart ?
Secondaire uniquement ; existe-t-il plusieurs façons de procéder, et quelles sont les différences ?
Merci pour la clarification !
Dart ne partage pas la mémoire au sein de plusieurs threads (isoler), donc...
extension Clone<T> on T {
/// in Flutter
Future<T> clone() => compute<T, T>((e) => e, this);
/// in Dart
Future<T> clone() async {
final receive = ReceivePort();
receive.sendPort.send(this);
return receive.first.then((e) => e as T).whenComplete(receive.close);
}
}
Essayer d'utiliser un Copiable interface fournie par Dart.
Il existe un moyen plus simple de résoudre ce problème utilisez simplement ...
opérateur par exemple, clone une Map
Map p = {'name' : 'parsa','age' : 27};
Map n = {...p};
Vous pouvez également le faire pour les propriétés des classes. Dans mon cas, j'avais besoin de cloner une propriété listée d'une classe. Donc :
class P1 {
List<String> names = [some data];
}
/// codes
P1 p = P1();
List<String> clonedList = [...p.names]
// now clonedList is an unreferenced type
Il n'y a pas de moyen intégré de cloner profondément un objet - vous devez fournir vous-même la méthode pour le faire.
J'ai souvent besoin de coder/décoder mes classes à partir de JSON, donc je fournis habituellement MyClass fromMap(Map)
y Map<String, dynamic> toJson()
méthodes. Elles peuvent être utilisées pour créer un clone profond en encodant d'abord l'objet en JSON puis en le décodant en retour.
Cependant, pour des raisons de performance, j'implémente généralement un système séparé de clone
à la place. C'est un travail de quelques minutes, mais je trouve que c'est souvent du temps bien utilisé.
Dans l'exemple ci-dessous, cloneSlow
utilise la technique JSON, et cloneFast
utilise la méthode du clone explicitement implémentée. Les impressions prouvent que le clone est réellement un clone profond, et pas seulement une copie de la référence à a
.
import 'dart:convert';
class A{
String a;
A(this.a);
factory A.fromMap(Map map){
return A(
map['a']
);
}
Map<String, dynamic> toJson(){
return {
'a': a
};
}
A cloneSlow(){
return A.fromMap(jsonDecode(jsonEncode(this)));
}
A cloneFast(){
return A(
a
);
}
@override
String toString() => 'A(a: $a)';
}
void main() {
A a = A('a');
A b = a.cloneFast();
b.a = 'b';
print('a: $a b: $b');
}
Un exemple de copie profonde dans dart.
void main() {
Person person1 = Person(
id: 1001,
firstName: 'John',
lastName: 'Doe',
email: 'john.doe@email.com',
alive: true);
Person person2 = Person(
id: person1.id,
firstName: person1.firstName,
lastName: person1.lastName,
email: person1.email,
alive: person1.alive);
print('Object: person1');
print('id : ${person1.id}');
print('fName : ${person1.firstName}');
print('lName : ${person1.lastName}');
print('email : ${person1.email}');
print('alive : ${person1.alive}');
print('=hashCode=: ${person1.hashCode}');
print('Object: person2');
print('id : ${person2.id}');
print('fName : ${person2.firstName}');
print('lName : ${person2.lastName}');
print('email : ${person2.email}');
print('alive : ${person2.alive}');
print('=hashCode=: ${person2.hashCode}');
}
class Person {
int id;
String firstName;
String lastName;
String email;
bool alive;
Person({this.id, this.firstName, this.lastName, this.email, this.alive});
}
Et le résultat ci-dessous.
id : 1001
fName : John
lName : Doe
email : john.doe@email.com
alive : true
=hashCode=: 515186678
Object: person2
id : 1001
fName : John
lName : Doe
email : john.doe@email.com
alive : true
=hashCode=: 686393765
Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.