标签: thread-safety

在C#实例方法中,'this'可以为null吗?

我有一种情况,很少有对象的队列出列空.对Enqueue的唯一调用是在类本身内:

m_DeltaQueue.Enqueue(this);
Run Code Online (Sandbox Code Playgroud)

很少,null在以下代码中从此队列中出列(静态方法):

while (m_DeltaQueue.Count > 0 && index++ < count)
    if ((m = m_DeltaQueue.Dequeue()) != null)
        m.ProcessDelta();
    else if (nullcount++ < 10)
    {
        Core.InvokeBroadcastEvent(AccessLevel.GameMaster, "A Rougue null exception was caught, m_DeltaQueue.Dequeue of a null occurred. Please inform an developer.");
        Console.WriteLine("m_DeltaQueue.Dequeue of a null occurred: m_DeltaQueue is not null. m_DeltaQueue.count:{0}", m_DeltaQueue.Count);
    }
Run Code Online (Sandbox Code Playgroud)

这是生成的错误报告:

[Jan 23 01:53:13]:m_DeltaQueue.发生null的取消:m_DeltaQueue不为null.m_DeltaQueue.count:345

关于如何在此队列中出现空值,我感到非常困惑.

在我写这篇文章时,我想知道这是否可能是线程同步的失败; 这是一个多线程应用程序,可能在另一个线程中同时发生入队或出队.

目前这是在.Net 4.0下,但它以前发生在3.5/2.0

更新:

这是我(希望是正确的)解决问题的方法,尽管下面的重要答案是同步问题,但这个解决方案已经明确了.

private static object _lock = new object();
private static Queue<Mobile> m_DeltaQueue = new Queue<Mobile>();
Run Code Online (Sandbox Code Playgroud)

排队:

    lock (_lock) …
Run Code Online (Sandbox Code Playgroud)

.net c# multithreading thread-safety

27
推荐指数
1
解决办法
3702
查看次数

是否可以从另一个线程观察部分构造的对象?

我经常听说在.NET 2.0内存模型中,写入始终使用释放围栏.这是真的?这是否意味着即使没有明确的内存屏障或锁定,也不可能在不同于创建它的线程上观察部分构造的对象(仅考虑引用类型)?我显然排除了构造函数泄漏this引用的情况.

例如,假设我们有不可变的引用类型:

public class Person
{
    public string Name { get; private set; }
    public int Age { get; private set; }

    public Person(string name, int age)
    {
        Name = name;
        Age = age;
    }
}
Run Code Online (Sandbox Code Playgroud)

是否可以使用以下代码观察除"John 20"和"Jack 21"之外的任何输出,例如"null 20"或"Jack 0"?

// We could make this volatile to freshen the read, but I don't want
// to complicate the core of the question.
private Person person;

private void Thread1()
{
    while (true)
    {
        var personCopy = person; …
Run Code Online (Sandbox Code Playgroud)

.net c# multithreading memory-model thread-safety

27
推荐指数
1
解决办法
1125
查看次数

何时在C#中使用锁定线程?

我有一个处理多个传入套接字连接的服务器,并创建2个不同的线程,以XML格式存储数据.

lock几乎在每个被称为异步的事件处理程序和代码的不同部分的2个线程中使用该语句用于线程安全.遗憾地使用这种方法我的应用程序显着减慢.

我试图完全不使用lock服务器执行速度非常快,甚至文件存储似乎也在提升; 但程序因30秒-1分钟后我不理解的原因而崩溃.工作的.

所以.我认为最好的方法是使用较少的锁或只在必要的地方使用它.因此,我有两个问题:

  1. 当我写入公共访问变量(C#列表)时,甚至当我从中读取时,是否需要锁定?

  2. 是否只需要在套接字处理程序或其他地方创建的异步线程中进行锁定?

有人可以给我一些关于如何操作的实用指南.我这次不会发布整个代码.发布大约2500行代码是没有意义的.

c# optimization multithreading thread-safety

27
推荐指数
2
解决办法
5326
查看次数

Java中的线程安全循环缓冲区

考虑一些并行运行的Web服务器实例.每个服务器都拥有对单个共享"状态管理器"的引用,其作用是保留N所有服务器的最后请求.

例如(N=3):

Server a: "Request id = ABCD"        Status keeper=["ABCD"]
Server b: "Request id = XYZZ"        Status keeper=["ABCD", "XYZZ"] 
Server c: "Request id = 1234"        Status keeper=["ABCD", "XYZZ", "1234"]
Server b: "Request id = FOO"         Status keeper=["XYZZ", "1234", "FOO"]
Server a: "Request id = BAR"         Status keeper=["1234", "FOO", "BAR"]
Run Code Online (Sandbox Code Playgroud)

在任何时间点,可以从监视应用程序调用"状态管理器",该应用程序读取NSLA报告的最后请求.

在Java中实现此生产者 - 消费者方案的最佳方法是什么,使Web服务器的优先级高于SLA报告?

CircularFifoBuffer似乎是保存请求的适当数据结构,但我不确定实现高效并发的最佳方法是什么.

java thread-safety circular-buffer

27
推荐指数
2
解决办法
2万
查看次数

可以从多个线程等待相同的任务 - 等待线程安全吗?

等待线程安全吗?似乎Task类是线程安全的,所以我猜等待它也是线程安全的,但我还没有在任何地方找到确认.线程安全也是定制awaiter的要求 - 我的意思是IsCompleted,GetAwaiter等方法?即如果这些方法不是线程安全的,那么等待是否是线程安全的?但是,我不希望很快就需要定制的等待者.

用户场景的一个示例:假设我有一个后台任务,它以异步方式返回结果,然后从多个线程使用:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;

namespace scratch1
{
    class Foo
    {
        Task<int> _task;

        public Foo()
        {
            _task = Task.Run(async () => { await Task.Delay(5000); return 5; });
        }

        // Called from multiple threads
        public async Task<int> Bar(int i)
        {
            return (await _task) + i;
        }
    }

    class Program
    {
        public static void Main(string[] args)
        {
            Foo foo = new Foo();

            List<Task> tasks = new List<Task>();
            foreach (var i in Enumerable.Range(0, 100))
            {
                tasks.Add(Task.Run(async …
Run Code Online (Sandbox Code Playgroud)

c# asynchronous thread-safety async-await

27
推荐指数
1
解决办法
5539
查看次数

IronPython中的多线程

我在IronPython中有一个"脚本类",我的应用程序中的脚本通过调用其实例上的方法来工作.我需要从多个线程实现调用脚本.这样做的正确方法是什么?

我有多个问题:

  1. ScriptScope线程安全的?信息是矛盾的.ScriptScope的文档说:"ScriptScope不是线程安全的.当多个线程可以访问同一个模块或者应该为每个线程复制时,主机应该锁定." 然而,IronRuby的使用相同的DLR和@JimmySchementi说"ScriptRuntime,ScriptEngine的,和ScriptScope都是线程安全的,设计线程之间使用.具体来说,ScriptScope使用一个线程安全的数据存储,所以ScriptScope可以在线程之间共享".

  2. 如果我创建多个ScriptScopes,那将意味着多次执行相同的初始化脚本.假设我运行了10个Python脚本文件,导入了5个程序集,并且总体上执行了相当多的代码以使"脚本对象"准备就绪.有没有办法避免为每个线程运行大量相同代码的时间和内存成本?

  3. ScriptScope变量线程静态(即应用ThreadStaticAttribute)和执行初始化为每个线程使用Task.Run的方式去?或者我应该使用TaskScheduler带有并发限制,因为多个范围的成本很高?

总的来说:如何正确实现在多个线程中的不同参数上运行相同的脚本?脚本必须同时执行,并且不得因竞争条件而崩溃.

.net multithreading ironpython thread-safety

27
推荐指数
1
解决办法
4268
查看次数

Objective-C中的原子属性与线程安全性

在我读过的大多数讨论中,它表明使属性原子不能保证它是线程安全的,它只是保证返回的值不会是一个对象写入它而另一个对象的垃圾.试图同时阅读它.

我理解这不是线程安全的,因为第三个对象可能正在编写它,而访问它的对象不会被垃圾回收,但是当多个对象同时写入它时,它不能完全确定它将返回哪个值时间,它可能会得到他们的任何价值观.

因此,当我们说它不会返回垃圾时,垃圾是否意味着如果一个对象是非原子的并且一个对象试图访问它而另一个对象正在写入它,那么它可能会在写入中间得到结果,并且只能获得写入所带来的部分不完整版本的更改?这就是"垃圾"在这个意义上意味着什么,以及什么原子属性有助于防止?

multithreading objective-c thread-safety atomicity ios

27
推荐指数
2
解决办法
2万
查看次数

我应该始终使我的java代码是线程安全的,还是出于性能原因,只在需要时才这样做?

如果我创建仅在单个线程中使用的类,我是否应该使它们成为线程安全的,即使我现在不需要它?可能会发生这种情况,我后来在多个线程中使用这个类,那时我可能会遇到竞争条件,如果我没有首先使用类线程安全的话,可能很难找到它们.或者我应该让这个类不是线程安全的,以获得更好的性能?但过早的优化是邪恶的.

不同的问题:如果需要,我应该让我的类线程安全(如果在多个线程中使用,否则不是)或者我应该优化这个问题然后需要(如果我看到同步占用处理时间的一个重要部分)?

如果我选择其中一种方法,是否有减少缺点的方法?或存在第三种可能性,我应该使用?

编辑:我说出这个问题出现在我脑海中的原因.在我们公司,我们编写了一个非常简单的用户管理,将数据写入属性文件.我在一个网络应用程序中使用它,经过一些工作后我得到了奇怪的错误,用户管理忘记了用户的属性(包括名称和密码)和角色.这非常令人讨厌但不能始终如一地重现,所以我认为这是竞争条件.由于我同步了所有从磁盘上读取和写入的方法,因此问题就消失了.所以我想,如果我们首先用同步编写了类,那么我可能已经避免了所有的麻烦了?

编辑2:当我查看实用程序员的提示时,我看到了提示#41:始终为并发设计.这并不是说所有代码都应该是线程安全的,但它说设计应该考虑到并发性.

java concurrency performance multithreading thread-safety

26
推荐指数
3
解决办法
4527
查看次数

代码重入与线程安全

"Code Re-entrancy""Thread Safety"的概念有什么区别?根据下面提到的链接,一段代码可以是它们中的任何一个,它们都是,或者都不是.

可重入和线程安全的代码

我无法清楚地理解解释.帮助将不胜感激.

multithreading thread-safety reentrancy

26
推荐指数
2
解决办法
5185
查看次数

将线程安全访问方法写入Windows窗体控件的最短方法

在这篇文章中:

http://msdn.microsoft.com/en-us/library/ms171728(VS.80).aspx

作者使用以下方法对Windows窗体控件进行线程安全调用:

private void SetText(string text)
{
    // InvokeRequired required compares the thread ID of the
    // calling thread to the thread ID of the creating thread.
    // If these threads are different, it returns true.
    if (this.textBox1.InvokeRequired)
    {    
        SetTextCallback d = new SetTextCallback(SetText);
        this.Invoke(d, new object[] { text });
    }
    else
    {
        this.textBox1.Text = text;
    }
}
Run Code Online (Sandbox Code Playgroud)

是否有更短的方法来完成同样的事情?

c# thread-safety

26
推荐指数
3
解决办法
2万
查看次数