Impossible d'ajouter des enregistrements à la liste passés en tant qu'objet à la méthode
J'ai cette classe:
Public class Error
{
public string ErrorMessage { get; set; }
}
public class Test
{
public int Id { get; set; }
public Import ImportResult { get; set; }
public List<Error> Errors { get; set; }
public void Start(object data)
{
object[] obj = data as object[];
string[] importList = { "Item1", "Item2", "Item3", "Item4" };
foreach (var item in importList)
{
object[] obj1 = new object[2];
obj1[0] = item;
obj1[1] = Errors;
this.ImportResult = new Import();
this.ImportResult.StartLongRunningProcess(obj1);//pass each import record to this method
}
}
}
public class Import
{
public int Id { get; set; }
public List<Error> Errors { get; set; }
public void StartLongRunningProcess(object data)
{
object[] datas = data as object[];
string import = datas[0].ToString();
try
{
// here I have along running process
}
// Here I store my error result in above list in long running process
catch (Exception ex)
{
datas[1]. // Here I would like to add record to error list of Test class.
Errors.Add(new Error
{
ErrorMessage = ex.message
});
}
}
}
Maintenant, ce que j'essaie de faire, c'est que je veux passer la liste des erreurs de la classe Test en tant que paramètre à la StartLongRunningProcess
méthode et à partir de là, je voudrais stocker tous les enregistrements d'erreur dans la variable d'erreur de la classe Test.
La raison de cela est que j'ai 1 méthode getCurrentData
qui est appelée toutes les 5 secondes pour obtenir l'enregistrement des erreurs en cours d'exécution de l'élément d'importation.Ainsi, à la fin de tous les éléments d'importation, j'aurais une liste d'erreurs prête pour tous les éléments d'importation.
public string getCurrentData() //called every 5 seconds to get latest data
{
var data = TestList.FirstOrDefault(x => x.Key == 100).Value;
response = new
{
errors = data.Errors.Select
(er => new
{
//error properties
}).ToList()
}
Le paramètre de StartLongRunningProcess est un objet car cette méthode s'exécute sur threadpool à partir de mon autre page, c'est pourquoi j'ai conservé le type de données en tant qu'objet pour les données de paramètre.
Je ne peux pas non plus faire de liste d'importation comme ci-dessous:
public List<Import> ImportResults = new List<Import>();
Question :
La méthode de démarrage de la classe de test s'exécute sur le pool de threads. Test.errors doit toujours être threadsafe ??
Compte tenu de votre ligne:
this.ImportResult.StartLongRunningProcess(obj1);//pass each import record to this method
vous appelez simplement la méthode de manière syncronale StartLongRunningProcess
. Dans ce cas particulier , il n'y a pas besoin de se soucier fil de sécurité , car les deux Start
et StartLongRunningProcess
sont d' exécution dans le même fil.
Mais alors il n'y a pas non plus besoin d'avoir StartLongRunningProcess
avec le object
paramètre;) Laissez-le prendre string importData, List<Error> errors
.
Mais si vous StartLongRunningProcess
commencez dans un autre thread (que Start
) et que vous en démarrez beaucoup en foreach
boucle, vous devriez évidemment vous soucier de la sécurité des threads. Parce que plus d'un StartLongRunningProcess
s'exécutant sur des threads différents peuvent appeler Errors.Add(error)
du même Test
objet.
... et maintenant je viens de remarquer votre dernière note dans la question initiale. Pourquoi tu ne peux pas faire ça? Que dit le compilateur?
D'abord. Il n'y a pas d' Errors
initialisation pour les deux classes. Faites-le dans le constructeur.
Deuxièmement, passez datas[1]. // Here i would like to add record to error list of Test class.
à:
(data[1] as List<Error>).Add(new Error ...);
Est-ce que ça marche?
Btw, Test.Errors
doit être de type thread-safe contre le Add
fonctionnement. Par exemple, vous pouvez utiliser ConcurrentQueue<T>
.