当前位置: 首页 > news >正文

【Java并发编程三】线程的基本使用一

基本使用一

 将类继承Runnable,创建Thread,然后调用Thread的start方法启动:

package myTest;public class myTest implements Runnable {public static void main(String[] args) throws InterruptedException {myTest test = new myTest();Thread thread = new Thread(test);System.out.println(thread.getState());thread.start();System.out.println(thread.getState());thread.sleep(1000);System.out.println(thread.getState());}public String sout() {return "test";}@Overridepublic void run() {System.out.println(this.sout());// System.out.println("runnning");}
}

查看Thread的start()方法

    public synchronized void start() {/*** This method is not invoked for the main method thread or "system"* group threads created/set up by the VM. Any new functionality added* to this method in the future may have to also be added to the VM.** A zero status value corresponds to state "NEW".*/if (threadStatus != 0)throw new IllegalThreadStateException();/* Notify the group that this thread is about to be started* so that it can be added to the group's list of threads* and the group's unstarted count can be decremented. */group.add(this);boolean started = false;try {start0();started = true;} finally {try {if (!started) {group.threadStartFailed(this);}} catch (Throwable ignore) {/* do nothing. If start0 threw a Throwable thenit will be passed up the call stack */}}}

查看start0()方法

 我们发现这里有一个Native关键字。Native Method就是一个java调用非java代码的接口。
 一个Native Method是这样一个java的方法:该方法是一个原生态方法,方法对应的实现不是在当前文件,而是在用其他语言(如C和C++)实现的文件中。

    private native void start0();

查看native native void start0()

 这是一个c++函数,几乎包含在thread类中的所有操作。

/* openjdk\jdk\src\share\native\java\lang\Thread.c */#include "jni.h"
#include "jvm.h"#include "java_lang_Thread.h"#define THD "Ljava/lang/Thread;"
#define OBJ "Ljava/lang/Object;"
#define STE "Ljava/lang/StackTraceElement;"
#define STR "Ljava/lang/String;"#define ARRAY_LENGTH(a) (sizeof(a)/sizeof(a[0]))static JNINativeMethod methods[] = {{"start0",           "()V",        (void *)&JVM_StartThread},{"stop0",            "(" OBJ ")V", (void *)&JVM_StopThread},{"isAlive",          "()Z",        (void *)&JVM_IsThreadAlive},{"suspend0",         "()V",        (void *)&JVM_SuspendThread},{"resume0",          "()V",        (void *)&JVM_ResumeThread},{"setPriority0",     "(I)V",       (void *)&JVM_SetThreadPriority},{"yield",            "()V",        (void *)&JVM_Yield},{"sleep",            "(J)V",       (void *)&JVM_Sleep},{"currentThread",    "()" THD,     (void *)&JVM_CurrentThread},{"countStackFrames", "()I",        (void *)&JVM_CountStackFrames},{"interrupt0",       "()V",        (void *)&JVM_Interrupt},{"isInterrupted",    "(Z)Z",       (void *)&JVM_IsInterrupted},{"holdsLock",        "(" OBJ ")Z", (void *)&JVM_HoldsLock},{"getThreads",        "()[" THD,   (void *)&JVM_GetAllThreads},{"dumpThreads",      "([" THD ")[[" STE, (void *)&JVM_DumpThreads},{"setNativeName",    "(" STR ")V", (void *)&JVM_SetNativeThreadName},
};#undef THD
#undef OBJ
#undef STE
#undef STRJNIEXPORT void JNICALL
Java_java_lang_Thread_registerNatives(JNIEnv *env, jclass cls)
{(*env)->RegisterNatives(env, cls, methods, ARRAY_LENGTH(methods));
}

查看JVM_StartThread

 发现它被一个叫做JVM_ENTRY给调用

JVM_ENTRY(void, JVM_StartThread(JNIEnv* env, jobject jthread))JVMWrapper("JVM_StartThread");JavaThread *native_thread = NULL;bool throw_illegal_thread_state = false;// We must release the Threads_lock before we can post a jvmti event// in Thread::start.{MutexLocker mu(Threads_lock);if (java_lang_Thread::thread(JNIHandles::resolve_non_null(jthread)) != NULL) {throw_illegal_thread_state = true;} else {jlong size =java_lang_Thread::stackSize(JNIHandles::resolve_non_null(jthread));size_t sz = size > 0 ? (size_t) size : 0;native_thread = new JavaThread(&thread_entry, sz);if (native_thread->osthread() != NULL) {// Note: the current thread is not being used within "prepare".native_thread->prepare(jthread);}}}if (throw_illegal_thread_state) {THROW(vmSymbols::java_lang_IllegalThreadStateException());}Thread::start(native_thread);JVM_END

 其中有一行

native_thread = new JavaThread(&thread_entry, sz);

 有native_thread,那这个JavaThread将一个thread_entry这个指针放入了构造函数中:

static void thread_entry(JavaThread* thread, TRAPS) {HandleMark hm(THREAD);Handle obj(THREAD, thread->threadObj());JavaValue result(T_VOID);JavaCalls::call_virtual(&result,obj,KlassHandle(THREAD,SystemDictionary::Thread_klass()),vmSymbolHandles::run_method_name(),    vmSymbolHandles::void_method_signature(),THREAD);}

 这个vmSymbolHandles::run_method_name(),调用了run的方法:

template(run_method_name,"run")

 成功的调用了run方法。所以,thread类在jvm的实现,cpp里面:

@Override
public void run() 
{    if (target != null){        target.run();    }
}

这里有一个target,通过它来判断,而这个target又在哪里?

private Runnable target;

 target在thread这个类中是被runnable所定义:

public interface Runnable {/*** When an object implementing interface <code>Runnable</code> is used* to create a thread, starting the thread causes the object's* <code>run</code> method to be called in that separately executing* thread.* <p>* The general contract of the method <code>run</code> is that it may* take any action whatsoever.** @see     java.lang.Thread#run()*/public abstract void run();
}

 它们之间的联系,从start到start0,再到native,再到jvm,再到cpp,其中的一个宏对象调用了run方法。

http://www.lryc.cn/news/234813.html

相关文章:

  • 企业邮箱认证指南:安全与高效的邮箱认证方法
  • Django(八、如何开启事务、介绍长见的字段类型和参数)
  • 机器学习第5天:多项式回归与学习曲线
  • MSYS2介绍及工具安装
  • Swift开发中:非逃逸闭包、逃逸闭包、自动闭包的区别
  • 栈结构应用-进制转换-辗转相除法
  • 【Azure 架构师学习笔记】-Azure Storage Account(6)- File Layer
  • idea 环境搭建及运行java后端源码
  • 掌握Shell:从新手到编程大师的Linux之旅
  • 有重复元素的快速排序
  • Bert浅谈
  • 产品运营的场景和运营策略
  • C#异常捕获try catch详细介绍
  • 切换阿里云ES方式及故障应急处理方案
  • CTFhub-RCE-过滤空格
  • 无需添加udid,ios企业证书的自助生成方法
  • 【PTA题目】6-20 使用函数判断完全平方数 分数 10
  • Nas搭建webdav服务器并同步Zotero科研文献
  • 一句话总结敏捷实践中不同方法
  • 【数据结构】线段树(点修区查)
  • Ansys Lumerical | 用于增强现实系统的表面浮雕光栅
  • QT day3作业
  • 【Ubuntu】设置永不息屏与安装 dconf-editor
  • gRPC 的原理 介绍带你从头了解gRPC
  • Apriori算法
  • 肖sir__linux讲解(2.1)
  • The ultimate UI kit and design system for Figma 组件库下载
  • Selenium——利用input标签上传文件
  • C++初阶 日期类的实现(下)
  • 大师学SwiftUI第16章 - UIKit框架集成