1. まず、スレッドを作成するいくつかの方法 (簡単なリスト) について説明します
1. Thread クラスを継承し、run メソッドをオーバーライドします:
1 2 3 4 5 6 7 8 9 10 11 12 13 | public class ExtendsThread extends Thread{
@Override
public void run() {
try {
System.out.println(Thread.currentThread().getName()+ "执行" );
} catch (Exception e){
}
}
public static void main(String[] args) {
new Thread( new ExtendsThread()).start();
}
}
|
ログイン後にコピー
2. Runnable インターフェイスを実装しますrun メソッドをオーバーライドします。メソッド:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 | public class ImplementsRunnable implements Runnable{
@Override
public void run() {
try {
System.out.println(Thread.currentThread().getName()+ "执行" );
} catch (Exception e){
}
}
public static void main(String[] args) {
new Thread( new ImplementsRunnable()).start();
new Thread( new Runnable() {
@Override
public void run() {
System.out.println(Thread.currentThread().getName()+ "执行" );
}
}, "匿名内部类实现Runnable接口的线程" );
}
}
|
ログイン後にコピー
3. Callable インターフェイスを実装し、FutureTask を使用してスレッドを作成します (戻り値を取得できます):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 | public class CallableAndFuture implements Callable<String> {
@Override
public String call() throws Exception {
Thread.sleep(3000);
System.out.println(Thread.currentThread().getName()+ "执行" );
return "success" ;
}
public static void main(String[] args) throws ExecutionException, InterruptedException {
FutureTask<String> futureTask = new FutureTask<>( new CallableAndFuture());
new Thread(futureTask).start();
String result = futureTask.get();
System.out.println(result);
}
}
|
ログイン後にコピー
4. スレッド プールを使用します。スレッドを作成するには (ここでは提供されたスレッド プール フレームワーク Executor を使用してスレッド プールを作成します):
1 2 3 4 5 6 7 8 9 10 11 | public class Executor {
public static void main(String[] args) {
ExecutorService executorService = Executors.newCachedThreadPool();
executorService.execute( new Runnable() {
@Override
public void run() {
System.out.println(Thread.currentThread().getName()+ "执行" );
}
});
}
}
|
ログイン後にコピー
2. 非同期タスクを実装するために Spring に付属する @Async アノテーションについて話しましょう
実際は非常に簡単で、アプリケーションのスタートアップ クラスに @EnableAsync アノテーションを配置するだけです。非同期アノテーションの使用を有効にして、ビジネス クラスのメソッドに @Async をマークします。
1 2 3 4 5 6 7 | @SpringBootApplication
@EnableAsync
public class AopApplication {
public static void main(String[] args) {
SpringApplication.run(AopApplication. class , args);
}
}
|
ログイン後にコピー
ビジネス クラス メソッド (例):
1 2 3 4 5 | @Async
public void insertDb(){
System.out.println( "2----->收到请求,写入数据库 " );
}
|
ログイン後にコピー
3. 次に、カスタム アノテーションを使用して非同期タスクを実装する方法を設計しましょう
最初にアノテーションを記述します:
1 2 3 4 5 6 | @Target({ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
public @ interface MyAsync {
boolean value() default false;
}
|
ログイン後にコピー
アノテーションの値をブール型に設定して、その true または false 値に基づいて非同期スレッドの作成を決定します。
これをビジネス クラスのメソッドに配置します:
1 2 3 4 5 | @MyAsync(value = true)
public void deleteDb(){
System.out.println( "delete------>数据删除" );
}
|
ログイン後にコピー
次に、AOP を使用してこの注釈をスキャンします:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | Aspect
@Component
public class AopUtils {
@Around(value = "@annotation(com.example.aop.Aop异步.MyAsync)" )
public void listenMyAsync(ProceedingJoinPoint joinPoint) throws Throwable {
MethodSignature signature = (MethodSignature) joinPoint.getSignature();
Method method = signature.getMethod();
MyAsync annotation = method.getAnnotation(MyAsync. class );
boolean value = annotation.value();
if (value)
new Thread( new Runnable() {
@SneakyThrows
@Override
public void run() {
joinPoint.proceed();
}
}).start();
else
joinPoint.proceed();
}
}
|
ログイン後にコピー
Around を使用して、実行用スレッド アノテーションを含むメソッドスタックをキャプチャした後、対応する接続ポイントオブジェクトを取得できます。
接続ポイント オブジェクト ProcedJoinPoint の getSignture メソッドを使用して署名を取得すると、署名をメソッド署名 MethdSignture 型に強制的に変換できるため、この型の getMethod メソッドを使用してメソッド自体を取得できます。アノテーションの属性を使用して値の true または false 値を直接取得することで、メソッドが同期的に渡されるか非同期的に渡されるかを決定します。 (ソース コードはリフレクション メカニズムを利用しています)。
以上がSpringboot が Aop キャプチャ アノテーションを使用してビジネスの非同期実行を実装する方法の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。