111,128
社区成员
发帖
与我相关
我的任务
分享
namespace 单例设计模式
{
class Program
{
static void Main(string[] args)
{
new Thread(new ThreadStart(SingleTown.getInstance().print)) { Name="线程1",IsBackground=true}.Start();
new Thread(new ThreadStart(SingleTown.getInstance().print)) { Name = "线程2", IsBackground = true }.Start();
new Thread(new ThreadStart(SingleTown.getInstance().print)) { Name = "线程3", IsBackground = true }.Start();
new Thread(new ThreadStart(SingleTown.getInstance().print)) { Name = "线程4", IsBackground = true }.Start();
Console.Read();
}
}
class SingleTown
{
private static SingleTown instance = null;
private static int count = 0;
private SingleTown()
{
}
public static SingleTown getInstance()
{
if (instance == null)
{
instance = new SingleTown();
count++;
}
return instance;
}
public void print()
{
Console.WriteLine(Thread.CurrentThread.Name+"打印实例个数"+count);
}
}
}

if (instance == null)
{
lock (_lock)
{
if (instance == null)
{
..............
(
也就是说,在 lock 之前要判断一次,然后在 lock (线程同步代码块)内部还要再次判断。这恰好反映了并发的特点。
不过一般为了“手懒”,少写第一个 if 判断。这样写固然有一点性能问题(经常多余进出 lock 代码块),但是如果觉得影响不大,也就这样写了。
public static SingleTown getInstance()
{
lock (_lock)
{
if (instance == null)
{
Thread.Sleep(1000);
instance = new SingleTown();
count++;
}
}
return instance;
}
结果就对了。。
第三种方法测试过 正常 因此以后用到的话还是选择第三种吧简洁高效 class Program
{
static void Main(string[] args)
{
for (int i = 0; i < 5; i++)
{
// new Thread(new ThreadStart(() => { SingleTown.getInstance().print(); })) { Name = "线程" + i, IsBackground = true }.Start();
new Thread(new ThreadStart(fun)) { Name = "线程" + i, IsBackground = true }.Start();
}
Console.Read();
}
private static void fun()
{
SingleTown.getInstance().print();
}
}
class SingleTown
{
private static SingleTown instance = null;
private static object _lock = new object();
private static int count = 0;
private SingleTown()
{
}
public static SingleTown getInstance()
{
if (instance == null)
{
lock (_lock)
{
Thread.Sleep(1000);
instance = new SingleTown();
count++;
}
}
return instance;
}
public void print()
{
Console.WriteLine(Thread.CurrentThread.Name + "打印实例个数" + count);
}
}
已修改 但是这个样子加了lock不应该是输出count的值就只为1 实例一次吗 为什么输出却是 1 2 3 4 5 /// <summary>
/// 单例模式
/// </summary>
/// <typeparam name="T">T</typeparam>
public class SingletonProvider<T> where T : new()
{
private static T m_instance;
private static readonly object sync = new object();
private SingletonProvider() { }
/// <summary>
/// 获取该类的单例
/// </summary>
public static T Instance
{
get
{
if (m_instance == null)
{
lock (sync)
{
if (m_instance == null)
{
m_instance = new T();
}
}
}
return m_instance;
}
}
} 这样 SingleTown.getInstance().print都是在主线程执行的,所以这个例子设计得出了问题。class Program
{
static void Main(string[] args)
{
new Thread(new ThreadStart(() => SingleTown.getInstance().print())) { Name = "线程1", IsBackground = true }.Start();
new Thread(new ThreadStart(() => SingleTown.getInstance().print())) { Name = "线程2", IsBackground = true }.Start();
new Thread(new ThreadStart(() => SingleTown.getInstance().print())) { Name = "线程3", IsBackground = true }.Start();
new Thread(new ThreadStart(() => SingleTown.getInstance().print())) { Name = "线程4", IsBackground = true }.Start();
Console.Read();
}
}
class SingleTown
{
private static SingleTown instance = null;
private static int count = 0;
private SingleTown()
{
}
public static SingleTown getInstance()
{
if (instance == null)
{
Thread.Sleep(1000);
instance = new SingleTown();
count++;
}
return instance;
}
public void print()
{
Console.WriteLine(Thread.CurrentThread.Name + "打印实例个数" + count);
}
}class Program
{
static void Main(string[] args)
{
Thread[] ths = new Thread[]
{
new Thread(NewThreadMethod) { Name = "线程1" }, //使用单独函数调用getInstance
new Thread(NewThreadMethod) { Name = "线程2" },
};
foreach (var item in ths)
item.Start();
Console.Read();
}
static void NewThreadMethod()
{
Thread.Sleep(500);
SingleTown.getInstance().print();
}
}
class SingleTown
{
private static SingleTown instance = null;
private static int count = 0;
private SingleTown()
{
}
public static SingleTown getInstance()
{
if (instance == null)
{
instance = new SingleTown();
Interlocked.Increment(ref count); //保证count能够+1
}
return instance;
}
public unsafe void print()
{
Console.WriteLine(Thread.CurrentThread.Name + "打印实例个数" + count);
}
}public static SingleTown getInstance()
{
if (instance == null)
{
Thread.Sleep(1000);//在这里加上这段
instance = new SingleTown();
count++;
}
return instance;
}
class Program
{
static void Main(string[] args)
{
var t1 = new Thread(new ThreadStart(Fun)) { Name = "线程1", IsBackground = true };
var t2 = new Thread(new ThreadStart(Fun)) { Name = "线程2", IsBackground = true };
var t3 = new Thread(new ThreadStart(Fun)) { Name = "线程3", IsBackground = true };
var t4 = new Thread(new ThreadStart(Fun)) { Name = "线程4", IsBackground = true };
t1.Start();
t2.Start();
t3.Start();
t4.Start();
//for (var i = 0; i < 5; i++)
//{
// var t = new Thread(new ThreadStart(Fun)) { Name = "线程1", IsBackground = true };
// t.Start();
//}
Console.Read();
}
private static void Fun()
{
SingleTown.getInstance().print();
}
}