线程:数组形成的栈,方法的调用,出栈入栈
Java代码对线程优先级设置不管用
都是立刻让出CPU,sleep不会释放锁锁,wait会释放锁,wait需要事先持有锁
在Java中,可以使用以下方法来查看线程信息:
使用Thread类的静态方法currentThread()来获取当前执行的线程对象。然后,可以使用该线程对象的实例方法getId()来获取线程的唯一标识符,getName()来获取线程的名称。
Thread currentThread = Thread.currentThread();
long threadId = currentThread.getId();
String threadName = currentThread.getName();
使用jps命令来查看Java进程的线程信息。打开命令行,进入到jdk的bin目录下,执行jps命令,可以看到当前Java线程的进程ID和名字。然后,使用jstack命令结合进程ID来打印出线程的信息。
jps
jstack <process id>
使用JConsole工具。在jdk的bin目录下有一个JConsole工具,打开它并连接到Java进程,可以在图形界面中查看线程信息。
使用VisualVM工具。VisualVM是一个功能强大的Java性能分析工具,可以查看Java进程的线程信息,包括线程的堆栈跟踪、CPU使用情况等。
使用Java的并发包(java.util.concurrent)。Java提供了一些并发工具类和接口,如ExecutorService、Future、CountDownLatch等,可以帮助开发者更好地管理和控制线程。
1、通过join控制
2、通过wait notify
3、通过共享变量
ThreadLocal?是 Java 中一个非常有用的类,它提供了线程局部变量。这些变量与普通的变量的区别在于,每个线程都拥有该变量的独立实例,互不干扰。这样,每个线程都可以修改自己的变量副本,而不会影响其他线程的副本。
使用?ThreadLocal?可以解决多线程中的数据同步问题,每个线程都拥有自己的数据副本,避免了对共享数据的并发访问冲突。
实现原理:每个线程调用都会拷贝一份对其进行操作;虚引用
CountDownLatch 是 Java 并发库中的一个类,它允许一个或多个线程等待其他线程完成操作。它提供了一种简单的方法来同步线程的执行。
CountDownLatch 的工作原理是,它维护一个计数器(count),初始化为一个特定的值。每个线程在完成自己的工作后,会调用 countDown() 方法来递减计数器。当计数器递减到 0 时,所有在 await() 方法上等待的线程都会被唤醒并继续执行。
它预先创建了若干数量的线程,并且不能由用户直接对线程的创建进行控制,在这个前提下重复使用固定或较为固定数目的线程来完成任务的执行。这样做的好处是,一方面,消除了频繁创建和消亡线程的系统资源开销,另一方面,面对过量任务的提交能够平缓的劣化。
public interface ThreadPool<Job extends Runnable> {
// 执行一个Job,这个Job需要实现Runnable
void execute(Job job);
// 关闭线程池
void shutdown();
// 增加工作者线程
void addWorkers(int num);
// 减少工作者线程
void removeWorker(int num);
// 得到正在等待执行的任务数量
int getJobSize();
}
有任务就会先交给核心线程数处理,核心线程数满了就会将线程放入队列中,加快线程的消耗
开启最大线程数的情况下,队列还是满的,就会采用拒绝策略
没有任务的核心线程也会处于运行状态;核心线程执行完成后处于空闲状态,没有满的话,后面的线程会新建一个执行,这样能提高运行速度
在finally块中释放锁,目的是保证在获取到锁之后,最终能够被释放;锁资源如果不被释放,会导致死锁的问题,解决办法:
Lock lock = new ReentrantLock();
lock.lock();
try {
} finally {
lock.unlock();
}
java中finally的作用
无论是否发生异常,都必须要执行的代码块。finally代码块通常用于资源的清理工作,比如关闭文件、释放网络连接等。