线程

synchronized

梦想与她 提交于 2020-04-07 23:14:16
概念 是利用锁的机制来实现同步的。 互斥性: 即在同一时间只允许一个线程持有某个对象锁,通过这种特性来实现多线程中的协调机制,这样在同一时间只有一个线程对需同步的代码块(复合操作)进行访问。互斥性我们也往往称为操作的原子性。 可见性: 必须确保在锁被释放之前,对共享变量所做的修改,对于随后获得该锁的另一个线程是可见的(即在获得锁时应获得最新共享变量的值),否则另一个线程可能是在本地缓存的某个副本上继续操作从而引起不一致。 用法 修饰静态方法: //同步静态方法 public synchronized static void methodName() { try { TimeUnit.SECONDS.sleep(2); System.out.println(Thread.currentThread().getName()+" aaa"); } catch (InterruptedException e) { e.printStackTrace(); } } public static void main(String[] args) { for (int i = 0; i < 5; i++) { new Thread(SynchronizedDemo::methodName).start(); } } 当synchronized作用于静态方法时,其锁就是当前类的class对象锁

Volatile与Synchronized的区别

橙三吉。 提交于 2020-04-07 23:13:32
java线程的内存模型 java的线程内存模型中定义了每个线程都有一份自己的共享变量副本(本地内存),里面存放自己私有的数据,其他线程不能直接访问,而一些共享变量则存在主内存中,供所有线程访问。 上图中,如果线程A和线程B要进行通信,就要经过主内存,比如线程B要获取线程A修改后的共享变量的值,要经过下面两步: (1)、线程A修改自己的共享变量副本,并刷新到了主内存中。 (2)、线程B读取主内存中被A更新过的共享变量的值,同步到自己的共享变量副本中。 总结:在java内存模型中,共享变量存放在主内存中,每个线程都有自己的本地内存,当多个线程同时访问一个数据的时候,可能本地内存没有及时刷新到主内存,所以就会发生线程安全问题。 java多线程中的三个特性:   原子性:即一个操作或者多个操作 要么全部执行并且执行的过程不会被任何因素打断,要么就都不执行。一个很经典的例子就是银行账户转账问题:比如从账户A向账户B转1000元,那么必然包括2个操作:从账户A减去1000元,往账户B加上1000元。这2个操作必须要具备原子性才能保证不出现一些意外的问题。   可见性:当多个线程访问同一个变量时,一个线程修改了这个变量的值,其他线程能够立即看得到修改的值。   有序性:就是程序执行的顺序按照代码的先后顺序执行。一般来说处理器为了提高程序运行效率,可能会对输入代码进行优化

如何在Python中使用线程?

馋奶兔 提交于 2020-04-07 21:33:20
问题: I am trying to understand threading in Python. 我试图了解Python中的线程。 I've looked at the documentation and examples, but quite frankly, many examples are overly sophisticated and I'm having trouble understanding them. 我看过文档和示例,但是坦率地说,许多示例过于复杂,我难以理解它们。 How do you clearly show tasks being divided for multi-threading? 您如何清楚地显示为多线程而划分的任务? 解决方案: 参考一: https://stackoom.com/question/BwXl/如何在Python中使用线程 参考二: https://oldbug.net/q/BwXl/How-to-use-threading-in-Python 来源: oschina 链接: https://my.oschina.net/u/3797416/blog/3223402

Linux下的睡眠函数sleep(),thread创建线程,求Linux系统的时间间隔

浪尽此生 提交于 2020-04-07 21:03:30
1、.cc文件下的睡眠函数: this_thread::sleep_for(chrono::seconds(1));睡眠1秒 2、eg: g++ multithread.cc -o multithread -std=c++11 -lpthread -std=C++11 :表示采用C++11标准 -lpthread :表示 线程库。 3、用thread创建线程 4、join()的作用:阻塞主线程。 5、线程函数带参数 6、使用Linux计算两时间戳间的时间: 1 struct timeval start_time,end_time; 2 gettimeofday(&start_time,NULL); 3 double time_used=end_time.tv_sec-start_time.tv_sec+(end_time.tv_usec-start_time.tv_usec)/1000000.0; 来源: https://www.cnblogs.com/technicist/p/12655752.html

线程之间的通信

独自空忆成欢 提交于 2020-04-07 19:58:29
一、为什么要线程通信? 1. 多个线程并发执行时, 在默认情况下CPU是 随机切换线程 的,当我们需要多个线程来 共同完成 一件任务,    并且我们希望他们 有规律 的执行, 那么多线程之间需要一些 协调通信 ,以此来帮我们达到 多线程共同操作一份数据 。 2.当然如果我们没有使用线程通信来使用多线程共同操作同一份数据的话,虽然可以实现,   但是在很大程度会造成多线程之间对同一共享变量的争夺,那样的话势必为造成很多错误和损失! 3.所以,我们才引出了线程之间的通信, 多线程之间的通信能够避免对同一共享变量的争夺。 二、什么是线程通信?   多个线程在处理 同一个资源 ,并且任务不同时,需要线程通信来帮助解决线程之间对同一个变量的 使用或操作 。   就是 多个线程在操作同一份数据时, 避免对同一共享变量的争夺 。   于是我们引出了 等待唤醒机制 :( wait() 、 notify() )   就是在一个线程进行了规定操作后,就进入等待状态( wait ), 等待其他线程执行完他们的指定代码过后 再将其唤醒( notify ); 1. 多个线程并发执行时, 在默认情况下CPU是 随机切换线程 的,当我们需要多个线程来 共同完成 一件任务,    并且我们希望他们 有规律 的执行, 那么多线程之间需要一些 协调通信 ,以此来帮我们达到 多线程共同操作一份数据 。 2

深度探索JFR

[亡魂溺海] 提交于 2020-04-07 19:54:35
2. JAVA 应用相关 2.4. Java Monitor 同步锁相关 主要是三种 Event: 当进入同步块,尝试获取锁的时候,产生 JavaMonitorEnter Event;当调用 Object.wait() 进入等待时,会产生 JavaMonitorWait Event;当 锁升级(另一种说法是锁膨胀)时,产生 JavaMonitorWait Event。 下面我从网上看到的这张图,有助于理解这三种事件: JavaMonitorEnter(Java Monitor Blocked):进入 Java Monitor Event。当需要进入同步代码时(字节码 monitorenter),会产生这个 Event。在 default.jfc 中默认为启用的,并且会追踪堆栈,阈值是 20ms;采集的信息包括:开始时间,持续时间,结束时间,线程,Monitor Address,Monitor Class,之前持有这个 Monitor 的线程。 JavaMonitorInflated(Java Monitor Inflated):发生锁升级的时候的 Event。在 default.jfc 中默认为启用的,并且会追踪堆栈,阈值是 20ms;采集的信息包括:开始时间,持续时间,结束时间,线程,Monitor Address,Monitor Class,锁升级原因

jvm主内存与工作内存

白昼怎懂夜的黑 提交于 2020-04-07 19:49:08
一、jvm主内存与工作内存 首先,JVM将内存组织为主内存和工作内存两个部分。 主内存主要包括本地方法区和堆。每个线程都有一个工作内存,工作内存中主要包括两个部分,一个是属于该线程私有的栈和对主存部分变量拷贝的寄存器(包括程序计数器PC和cup工作的高速缓存区)。 1.所有的变量都存储在主内存中(虚拟机内存的一部分),对于所有线程都是共享的。 2.每条线程都有自己的工作内存,工作内存中保存的是主存中某些变量的拷贝,线程对变量的所有操作都必须在工作内存中进行,而不能直接读写主内存中的变量。 3.线程之间无法直接访问对方的工作内存中的变量,线程间变量的传递均需要通过主内存来完成。 JVM规范定义了线程对内存间交互操作: Lock(锁定):作用于主内存中的变量,把一个变量标识为一条线程独占的状态。 Read(读取):作用于主内存中的变量,把一个变量的值从主内存传输到线程的工作内存中。 Load(加载):作用于工作内存中的变量,把read操作从主内存中得到的变量的值放入工作内存的变量副本中。 Use(使用):作用于工作内存中的变量,把工作内存中一个变量的值传递给执行引擎。 Assign(赋值):作用于工作内存中的变量,把一个从执行引擎接收到的值赋值给工作内存中的变量。 Store(存储):作用于工作内存中的变量,把工作内存中的一个变量的值传送到主内存中。 Write(写入)

ThreadPoolExecutor 的基本原理

﹥>﹥吖頭↗ 提交于 2020-04-07 15:37:21
先说下 ThreadPoolExecutor 的基本原理: 1. 当提交一个任务时,如果线程数没有达到coreSize,那么就会新建一个线程,并绑定该任务,直到数量到达coreSize前都不会重用之前的线程 2.到达后,提交的任务都会放到一个等待队列中进行等待,线程池中的线程会使用take()阻塞的从等待队列拿任务 3.当队列有界,并且线程不能及时取走队列中的任务,等待队列有可能会满,那么线程池将会创建临时线程来执行任务 4.临时线程 通过poll(keepAliveTime,timeUnit)来执行任务,如果到了keepAliveTime还取不到,那么会被回收掉,临时线程的数量不能大于 maxPoolSize - coreSize 5.当线程数到达maxSize后,将会执行拒绝策略RejectedExecutionHandler,包括抛异常,静默拒绝,抛弃最old任务,使用原远程执行等策略 知道了原理你大概就知道线程被如何管理了 当一个task执行完,如果线程数小于coreSize,那么这个线程就会一直存在线程池中, 如果是临时线程,在等待keepAliveTime后,将会被回收掉 来源: https://www.cnblogs.com/zjm-1/p/12653532.html

线程同步之互斥量

你说的曾经没有我的故事 提交于 2020-04-07 11:53:29
操作系统编程--线程同步问题 生产者和消费者问题 互斥量是最简单的线程同步的方法 互斥量(互斥锁),处于两态之一的变量:解锁和加锁 两个状态可以保证资源访问的串行 操作系统直接提供了互斥量的API 开发者可以直接使用API完成资源的加锁、解锁操作 具体操作 ◆ pthread_mutex_t //用于定义线程互斥锁对象 ◆ pthread_mutex_lock(&mutex) //上锁操作 ◆ pthread_mutex_unlock(&mutex) //开锁操作 #include <stdio.h> #include <stdlib.h> #include <unistd.h> #include <pthread.h> #include <vector> pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER; int num = 0; void *producer(void*){ int times = 10000000; while(times --){ //不加锁操作则会导致出现共享资源不统一问题 即num 最后不为0 pthread_mutex_lock(&mutex); num += 1; pthread_mutex_unlock(&mutex); } } void *comsumer(void*){ int times =

java中线程队列BlockingQueue的用法

試著忘記壹切 提交于 2020-04-07 11:09:48
在新增的Concurrent包中,BlockingQueue很好的解决了多线程中,如何高效安全“传输”数据的问题。通过这些高效并且线程安全的队列类,为我们快速搭建高质量的多线程程序带来极大的便利。本文详细介绍了BlockingQueue家庭中的所有成员,包括他们各自的功能以及常见使用场景。 [ @more @] 认识BlockingQueue 阻塞队列,顾名思义,首先它是一个队列,而一个队列在数据结构中所起的作用大致如下图所示: 从上图我们可以很清楚看到,通过一个共享的队列,可以使得数据由队列的一端输入,从另外一端输出; 常用的队列主要有以下两种:(当然通过不同的实现方式,还可以延伸出很多不同类型的队列,DelayQueue就是其中的一种)   先进先出(FIFO):先插入的队列的元素也最先出队列,类似于排队的功能。从某种程度上来说这种队列也体现了一种公平性。   后进先出(LIFO):后插入队列的元素最先出队列,这种队列优先处理最近发生的事件。 多线程环境中,通过队列可以很容易实现数据共享,比如经典的“生产者”和“消费者”模型中,通过队列可以很便利地实现两者之间的数据共享。假设我们有若干生产者线程,另外又有若干个消费者线程。如果生产者线程需要把准备好的数据共享给消费者线程,利用队列的方式来传递数据,就可以很方便地解决他们之间的数据共享问题。但如果生产者和消费者在某个时间段内