apache禁用不安全的http法_快看,i++真的不安全

上期文章讲到“i++;”本身是一个线程不安全的操作,原因是操作不是原子性的,存在取值和赋值的两个过程,但是究竟怎么会不安全呢?本期借助一个“vmlens”的项目来演示为何会发生线程不安全的情况。文末是vmlens简介。

测试代码:

public class TestCounter {
	private volatile int i = 0;
	@Interleave
	public void increment() {
	 i++;	
	}
	@Test
	public void testUpdate() throws InterruptedException	{
		Thread first = new Thread( () ->   {increment();} ) ;
		Thread second = new Thread( () ->   {increment();} ) ;
		first.start();
		second.start();
		first.join();
		second.join();
		
	}	
	@After
	public void checkResult() {
		assertEquals( 2 , i );
	}	
}

重要的是pom.xml文件配置:

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
  <modelVersion>4.0.0</modelVersion>
  <groupId>com.vmlens</groupId>
  <artifactId>examples</artifactId>
  <version>0.0.1-SNAPSHOT</version>
  <packaging>jar</packaging>

  <name>examples</name>
  <url>http://maven.apache.org</url>

 <pluginRepositories>
  <pluginRepository>
    <id>vmlens</id>
    <url>http://vmlens.com/download</url>
  </pluginRepository>
</pluginRepositories>


  <properties>
    <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
  </properties>

  <dependencies>
   		<dependency>
			<groupId>com.vmlens</groupId>
			<artifactId>annotation</artifactId>
			<version>1.0.2</version>
			<scope>test</scope>
		</dependency>
  
  
    <dependency>
      <groupId>junit</groupId>
      <artifactId>junit</artifactId>
      <version>4.8.2</version>
      <scope>test</scope>
    </dependency>
  </dependencies>
   <build>
    <pluginManagement>
    <plugins>
    
     
    <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-compiler-plugin</artifactId>
        <version>3.5.1</version>
        <configuration>
          <source>1.8</source>
          <target>1.8</target>
        </configuration>
      </plugin>
    </plugins>
 </pluginManagement>
 
  <plugins>
  			<plugin>
				<groupId>org.apache.maven.plugins</groupId>
				<artifactId>maven-surefire-plugin</artifactId>
				<version>3.0.0-M3</version>
				<configuration>
					<includes>
						<include>none</include>
					</includes>
				</configuration>
			</plugin>
 	<plugin>
				<groupId>com.vmlens</groupId>
				<artifactId>interleave</artifactId>
				<version>1.0.4</version>
				<!-- start regression test -->
				<configuration>
					<trimStackTrace>false</trimStackTrace>
									<includes>
		<include>com.vmlens.examples.doNotCombine.TestCounter</include>
					</includes>
				</configuration>
           </plugin>
      </plugins>
  </build>
  </project>

接下来是vmlens的报告:

2055822cf916de9b67a7f89656f51ebb.png

从图中我们可以看出在两个线程同时执行“i++;”的时候,两个线程都先后读取到了i的值“0”,然后先后完成了计算“i+1”,最后又先后给i赋值“1”,导致测试用例执行失败。

介绍一下这个插件:

“vmlens”是一款测试java多线程的工具。

1. 需要测试多个线程访问相同内存位置或监视器的应用程序的所有部分。vmlens显示多个线程访问相同内存位置或监视器的所有位置。

2. vmlens插入等待,在测试期间通知指令并重新运行测试,直到测试所有线程交错。这与数据竞争和死锁的自动检测一起导致系统和可重复的测试。

3. 通过查看多个线程以何种方式访问​​相同状态,您可以减少共享状态的数量。

4. 较少共享状态意味着需要较少的同步监视器。

下面是作者托马斯原文:

```

Hello!

Do you love to write bug-free software? Me too!

It always bothers me when I can not test something. That's why I created vmlens, a tool to test multithreaded java.

Now 4 years and countless tests later vmlens enables you to test multi-threaded java systematic and reproducible. And like vmlens now let my completely test vmlens, vmlens let you test the multithreaded part of your application

Enjoy writing concurrent software secured by tests.

Cheers, Thomas

```

作者本人照片:

48d3b712c01203be3eb592976a75c95c.png
readme.markdown · 八音弦/tester - 码云 Gitee.com​gitee.com
1643203622f9405b9e0fe8ca2dcd1a25.png
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值