最近在做一些代码整理工作,涉及到List 线程安全问题,查了一些资料。网上有些资料说List 增减成员(Add , Remove) 是安全的,但不保证成员属性值访问安全性,及禁止对 List 跨线程遍历访问, 如 foreach 遍历。
可以想象,有些跨线程操作(Add , Remove)List 集合时, 恰好 另一个线程正在通过 foreach遍历, 这时会抛出异常) 。 有改进方案用 for 替代 foreach ,这样仍会报下标越界错误。
因此 , 跨线程遍历list 不安全毋庸置疑。 对List 增减成员是否安全,需要验证才知道。

如下代码:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading; namespace testQueue
{
class Program
{
static List<int> list = new List<int>();
static ManualResetEvent[] manu;
static object LockList = new object(); static void Main(string[] args)
{
manu = new ManualResetEvent[2];
manu[0] = new ManualResetEvent(false);
manu[1] = new ManualResetEvent(false); ThreadPool.QueueUserWorkItem(new WaitCallback(Task1));
ThreadPool.QueueUserWorkItem(new WaitCallback(Task2)); //等待完成
ManualResetEvent.WaitAll(manu); //统计结果:
Console.WriteLine("count:{0}", list.Count); Console.ReadKey();
} public static void Task1(object obj)
{
// lock (LockList)
// {
for (int i = 0; i < 5000000; i++)
{
list.Add(i);
}
// } Console.WriteLine("Task1 complete!");
manu[0].Set();
} public static void Task2(object obj)
{
// lock (LockList)
// {
for (int i = 0; i < 5000000; i++)
{
list.Add(i);
}
// }
Console.WriteLine("Task2 complete!");
manu[1].Set();
}
}
}

结果:

我们知道, List 集合大小是动态分配的,此处表明,分配List 大小,与对 List 操作 , 应保证在同一线程。  为了避免List 运行中分配大小,在初使化时,设置了List 大小:

static List<int> list = new List<int>(10000000);

再看看结果:

增加线程锁结果:

结论:

此处表明,使用 List 跨线程操作,增减成员也需加锁。否则会有各种问题。
有关线程集合安全访问, 微软在 .Net Framework 4 时,提供了线程安全集合命名空间:

System.Collections.Concurrent

List 集合线程安全测试的更多相关文章

  1. java集合线程安全测试

    package com.cxy; import java.util.HashMap; import java.util.Hashtable; import java.util.Map; import ...

  2. Python_线程、线程效率测试、数据隔离测试、主线程和子线程

    0.进程中的概念 三状态:就绪.运行.阻塞 就绪(Ready):当进程已分配到除CPU以外的所有必要资源,只要获得处理机便可立即执行,这时的进程状态成为就绪状态. 执行/运行(Running)状态:当 ...

  3. JUC---07解决集合线程不安全

    一.ArrayList是线程不安全的,可以使用以下操作解决: 1.使用相同功能的集合类替换,比如Vector集合是线程安全的,他们实现的接口都是一样的,但是Vector类是在jdk1.0出现的,不推荐 ...

  4. ArrayList的线程安全测试

    public class TestThread implements Runnable{ private List list; CountDownLatch cdl; public TestThrea ...

  5. Ultimate thread group线程组和Stepping thread group线程组测试场景

    Ultimate thread group线程组 当测试需求是要求进行波浪型的压力测试场景时,使用该线程组,例如:测试场景总共有10个线程,然后分为三个波段进行测试,每个波段负载策略设置为一样,如图:

  6. [原创] JAVA 递归线程池测试 ExecutorService / ForkJoinPool

    测试工具使用递归的方式获取子进程的Msg消息,目前有2种常用的ExecutorService / ForkJoinPool 为了测试哪种效果较好,我们来写个测试Demo,循环5555555次+1(加锁 ...

  7. java集合 线程安全

    1.快速失败(fail-fast)和安全失败(fail-safe)? 一:快速失败(fail—fast) 在用迭代器遍历一个集合对象时,如果遍历过程中对集合对象的内容进行了修改(增加.删除.修改),则 ...

  8. Java 集合 线程安全

    Java中常用的集合框架中的实现类HashSet.TreeSet.ArrayList.ArrayDeque.LinkedList.HashMap.TreeMap都是线程不安全的,如果多个线程同时访问它 ...

  9. C# 使用ConcurrentBag类处理集合线程安全问题

    在日常的开发中,经常会遇到多个线程对同一个集合进行读写操作,就难免会出现线程安全问题. 以下代码,如果使用List<T>就会遇到问题:System.InvalidOperationExce ...

随机推荐

  1. SLAM前端技术选择思考

    以前是专门做室内定位技术研究的,先后学习和分析了多种基于电磁的室内定位技术,如WiFi指纹定位(先后出现过RSSI.CTF.CIR多种指纹特征).WiFi ToF定位.低功耗蓝牙BLE以及iBeaco ...

  2. C#知识点总结系列:5、CLR的组成和运转

    clr基本 CLR(Common Language Runtime)是一个可由多种编程语言使用的“运行时”.(例如:c#,c++/cli,vb,f#,ironpython,ironruby,il... ...

  3. Openstack+Kubernetes+Docker微服务实践之路--Docker和Registry2

    渐入佳境,我们开始比较具体的工作,由于Docker是一个基础组件,所以本文的主题是Docker和Registry2. 底层系统基于Centos7,先在一台云主机上安装Docker,Docker的安装非 ...

  4. github项目配置

    准备工作: 下载一个git:  https://git-scm.com/downloads 1.登陆到github 登陆地址:https://github.com/login 2.创建新项目 3.配置 ...

  5. github desktop 在线安装失败解决方案

    1.问题概述 我的OS是Windows8.1 64位,尝试安装github desktop,始终安装失败:进度到50%左右就炸了.提示说:网络出错.(我100M电信,网络出错?我一直都在上网好吗). ...

  6. Http referer origin

    为了防止CSRF的攻击,我们建议修改浏览器在发送POST请求的时候加上一个Origin字段,这个Origin字段主要是用来标识出最初请求是从哪里发起的.如果浏览器不能确定源在哪里,那么在发送的请求里面 ...

  7. Python_Day8_面向对象编程进阶

    本节内容: 面向对象高级语法部分异常处理 经典类vs新式类 静态方法.类方法.属性方法 类的特殊方法 反射 Socket开发基础 经典类vs新式类 classical vs new style: 经典 ...

  8. sqlservr (708) 打开日志文件 C:\Windows\system32\LogFiles\Sum\Api.log 时出现错误 -1032 (0xfffffbf8)

    在windows server 2012 standard上新安装好的SQL Server 2014,查看错误日志,发现此报错 sqlservr (708) 打开日志文件 C:\Windows\sys ...

  9. centos7装机和初步运维

    1.装机-制作U盘启动盘 CentOS7是一个比较新的版本.在服务器领域用得比较多.因为前安装软件可能没有Ubuntu那样方便,所以桌面领域好像不是很多. https://www.centos.org ...

  10. &nbsp;空格用法

    记录一下,空格的转义字符分为如下几种:平时一般用的是 1.  &160#;不断行的空白(1个字符宽度)2.  &8194#;半个空白(1个字符宽度)3.  &8195#;一个空 ...