简体   繁体   English

无法使用 Project Loom 的虚拟线程

[英]Not able us Virtual Threads using Project Loom

I was exploring the Virtual Threads in Project Loom.我正在探索 Project Loom 中的虚拟线程。 The Documents say it as straight forward with simple lines of code as below:文档用以下简单的代码行直截了当地说:

Thread.startVirtualThread(() -> {
    System.out.println("Hello, Loom!");
});

Or或者

Thread t = Thread.builder().virtual().task(() -> { ... }).start();

I have tried both of them, For the first one, I receive an error The method startVirtualThread(() -> {}) is undefined for the type Thread我已经尝试了它们,对于第一个,我收到一个错误The method startVirtualThread(() -> {}) is undefined for the type Thread

And for the second one - The method builder() is undefined for the type Thread而对于第二个- 方法builder()未定义 Thread 类型

One browsing, found that lombok is required, Installed lombok as well.一浏览,发现需要lombok,也安装了lombok。 However it doesn't show up in Eclipse About section, I am able to use lombok, But still my issue is not resolved.但是它没有出现在 Eclipse 关于部分,我可以使用 lombok,但我的问题仍然没有解决。

Below link show the documentation, I am referring to.下面的链接显示文档,我指的是。

enter link description here 在此处输入链接描述

Sample Code:示例代码:

 public class threads {
    public void simpleThread() {
        Thread start = Thread.builder().virtual().task(() -> {
            System.out.println("Hello World");
        }).start();
        Thread.startVirtualThread(() -> {
            System.out.println("Hello, Loom!");
        });
    }
    public static void main(String[] args) {
        // TODO Auto-generated method stub
        threads trd = new threads();
        trd.simpleThread();
    }
}

在此处输入图像描述

It looks like older versions of Eclipse is giving a compilation error when calling the new Thread methods related to Loom.看起来旧版本的 Eclipse 在调用与 Loom 相关的新 Thread 方法时出现编译错误。

Please try to use the latest Eclipse ( currently 2020-09 ) with an OpenJDK Project Loom Early-Access Build .请尝试将最新的 Eclipse( 当前 2020-09 )与OpenJDK Project Loom Early-Access Build一起使用。

You can make sure that this is an Eclipse related issue by compiling and running your program directly from the command line (using javac and java commands).您可以通过直接从命令行编译和运行程序(使用javacjava命令)来确保这是 Eclipse 相关问题。

For ubuntu system: Set the java 16 path in.bashrc file.对于ubuntu系统:在.bashrc文件中设置java 16个路径。 Make sure only have java 16 path present in the file.确保文件中仅存在 java 16 路径。 If any other java path is mentioned then following command may not work.如果提到任何其他 java 路径,则以下命令可能不起作用。

If you want to confirm if the java version is set to 16 then execute java -version .如果要确认 java 版本是否设置为 16,则执行java -version
Then you can try directly compile your loom class through following command.然后您可以尝试通过以下命令直接编译您的织机 class。

javac className.java 

java className

It worked for me.它对我有用。

Even when you get the compilation problems go away, this might or might not print anything.即使您遇到编译问题 go ,这也可能会或可能不会打印任何内容。

A virtual thread needs a carrier (a native thread to be executed on);虚拟线程需要一个carrier (要在其上执行的本机线程); and if the native thread finishes earlier then the virtual one starts, there is no such carrier;如果本机线程完成得早于虚拟线程开始,则没有这样的载体; thus you get no printing.因此你没有打印。 There are a couple of ways to work around that.有几种方法可以解决这个问题。

The simplest (just to see that this works), is to make the carrier threads sleep for a short while:最简单的(只是为了看看这是否有效),是让carrier线程休眠一小会儿:

 Thread.startVirtualThread(() -> {
        while (true) {
            System.out.println("trying " + Thread.currentThread().getName());
        }
    });

    LockSupport.parkNanos(TimeUnit.MILLISECONDS.toNanos(10));

On my machine this gives enough time for some output to be generated.在我的机器上,这为生成一些 output 提供了足够的时间。

Another way would be join on the carrier :另一种方法是加入carrier

    Thread t = Thread.startVirtualThread(() -> {
         System.out.println("trying " + Thread.currentThread().getName());
    });

    t.join();

This works for demo purposes, but in real life you probably need an executor.这适用于演示目的,但在现实生活中您可能需要一个执行器。 One way to supply it would be via:提供它的一种方法是:

   Thread.builder()
          .virtual(Executors.newFixedThreadPool(1))
          .task(() -> {
              System.out.println("started");
          })
          .build()
          .start();

    System.out.println("done");

You can even use Executors::newVirtualThreadExecutor where the current documentation states:您甚至可以使用Executors::newVirtualThreadExecutor当前文档中指出:

Creates an Executor that starts a new virtual thread for each task创建一个 Executor,为每个任务启动一个新的虚拟线程

So what you could do, is something like:所以你可以做的是:

    ExecutorService service = Executors.newVirtualThreadExecutor();

    service.execute(() -> {
        System.out.println(Thread.currentThread().getId());
    });

    service.execute(() -> {
        System.out.println(Thread.currentThread().getId());
    });

    LockSupport.parkNanos(TimeUnit.MILLISECONDS.toNanos(10));

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM