C# 修改并发容器中存储的元素时是否需要同步对象?

C# 修改并发容器中存储的元素时是否需要同步对象?,c#,.net,multithreading,C#,.net,Multithreading,我有一个简单的课程: public class TaskResult { public TaskResult() { CompletedSoFar = 0; Done = false; } [DataMember(Order = 0)] public int CompletedSoFar { get; set; } [DataMember(Order = 1)] public bool Done { ge

我有一个简单的课程:

public class TaskResult
{
    public TaskResult()
    {
        CompletedSoFar = 0;
        Done = false;
    }

    [DataMember(Order = 0)]
    public int CompletedSoFar { get; set; }

    [DataMember(Order = 1)]
    public bool Done { get; set; }   
}
其类型的对象存储在ConcurrentDictionary中:

private static ConcurrentDictionary<Guid, TaskResult> _results;

我是否可以在没有同步对象的情况下修改值(即CompletedSoFar、Done)?

如果尝试,是否会引发异常?由于您正在修改本机类型(整数),因此我不希望出现异常,这些类型无法锁定,并且可以在多个线程上安全访问。但是,在多个线程中更改此类(状态)类型时应小心,因为这可能会以意外的方式更改行为,并且很难跟踪

在修改它们时不会引发异常。然后,您可以(技术上)这样做,但我建议您(如果可能)创建一些可以管理的“同步对象”(阻止/允许)对此特定对象进行更改,并且能够(出于调试目的)存储更改和调用者。此外,如果您想更改其他非本机类型,此对象将派上用场,因此这是代码扩展性的良好实践
public TaskResult DoWork(int[] ids)
{
    var cancelSource = new CancellationTokenSource();
    var result = new TaskResult();
    _results[Guid.NewGuid()] = result;

    var task = System.Threading.Tasks.Task.Factory.StartNew(() =>
    {
        try
        {
            foreach (var id in ids)
            {
                cancelSource.Token.ThrowIfCancellationRequested();
                // Do work...
                result.CompletedSoFar++; // Increment work completed so far
            }

            result.Done = true; // Work now done
        }
        catch
        {
            throw;
        }
    }, cancelSource.Token);

    return result;
}