当前位置:   article > 正文

高级Java开发工程师手把手教你用AI人工智能帮你写JAVA代码实际案例二(生成自定义springboot定时器组件)全网唯一_ai 编程案例 java 开发

ai 编程案例 java 开发

高级Java开发工程师手把手教你用AI人工智能帮你写JAVA代码实际案例二全网唯一

一、需求背景案例说明

笔者有个实际的生产项目,想自己自定义定时器到数据库表里面,不想配置到配置文件里面,很麻烦!这次想用AI帮我写代码!Java springboot 环境!
数据库设计为:

CREATE TABLE `timer_config`  (
  `id` int(0) NOT NULL AUTO_INCREMENT,
  `timer_config` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '定时器配置:0 10 * * * ?',
  `class_method_name` text CHARACTER SET utf8 COLLATE utf8_general_ci NULL COMMENT '执行类方法名称',
  `remark` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '备注信息',
  PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;

-- ----------------------------
-- Records of md_timer_config
-- ----------------------------
INSERT INTO `timer_config` VALUES (1, '0 0 * * * ?', 'nasenServiceImpl.Task1', '方法1');
INSERT INTO `timer_config` VALUES (2, '0 5 * * * ?', 'nasenServiceImpl.Task2', '方法2');
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13

大家按照我的训练人工智能的思路往下走,AI还是需要引导与指导的!笔者把思路方法写下来!

二、训练指导AI的方法步骤

训练AI口令步骤一

提问口令:

下面是mysql的一个定时器配置表!
CREATE TABLE `timer_config`  (
  `id` int(0) NOT NULL AUTO_INCREMENT,
  `timer_config` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '定时器配置:0 10 * * * ?',
  `class_method_name` text CHARACTER SET utf8 COLLATE utf8_general_ci NULL COMMENT '执行类方法名称',
  `remark` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '备注信息',
  PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Dynamic;

-- ----------------------------
-- Records of md_timer_config
-- ----------------------------
INSERT INTO `timer_config` VALUES (1, '0 0 * * * ?', 'nasenServiceImpl.Task1', '方法1');
INSERT INTO `timer_config` VALUES (2, '0 5 * * * ?', 'nasenServiceImpl.Task2', '方法2');
下面是java代码spingboot的定时器调度的例子:
@EnableScheduling
@Component
public class AutoConfigTaskschedule {
	@Autowired
    private nasenServiceImpl nasenServiceImpl;
    @Scheduled(cron = "0 0 * * * ?")
    public void task1() {
    	 nasenServiceImpl.Task1();
    }

    @Scheduled(cron = "0 5 * * * ?")
    public void task2() {
    	nasenServiceImpl.Task2();
    }

}

你帮我修改代码,读取数据库的这个配置表,并动态的执行配置表里面的定时器任务!帮我把Java代码写出来
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33

注意:你要提前给AI一个引导,这个引导是一个方向,比如你给他建表语句,跟你项目中已经写好的定时器的一个例子,AI可以读懂,给你项目大概方向的代码跟实现!

AI回复:

以下是修改后的 Java 代码,用于读取数据库中的定时器配置表,并动态执行配置表中的定时器任务:

import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;

@EnableScheduling
@Component
public class DynamicTaskScheduler {

    @Autowired
    private DataSource dataSource; // 注入数据源

    @Scheduled(cron = "0 * * * *?") // 定期执行加载任务配置的操作
    public void loadTasks() {
        try (Connection connection = dataSource.getConnection()) {
            String query = "SELECT timer_config, class_method_name FROM timer_config";
            try (PreparedStatement statement = connection.prepareStatement(query);
                 ResultSet resultSet = statement.executeQuery()) {
                while (resultSet.next()) {
                    String timerConfig = resultSet.getString("timer_config");
                    String classMethodName = resultSet.getString("class_method_name");

                    // 根据配置创建定时器任务
                    @Scheduled(cron = timerConfig)
                    public void performTask() {
                        nasenServiceImpl.getClass().getMethod(classMethodName).invoke(nasenServiceImpl);
                    }
                }
            }
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33

在上述代码中,通过 loadTasks 方法定期从数据库中加载任务配置。使用 DataSource 注入数据源,并执行查询操作获取定时器配置和对应的类方法名称。然后,根据配置动态创建定时器任务,并通过反射机制调用指定类的指定方法。

请确保已正确配置数据源,并根据实际情况进行调整和扩展。

这个代码还是有些错误的,所以我们要继续引导AI
这个代码经过测试是错误的,还得继续引导!

训练AI口令步骤二

提问口令:

@Autowired
private DataSource dataSource; // 注入数据源

@Scheduled(cron = "0 * * * *?") // 定期执行加载任务配置的操作
public void loadTasks() {
    try (Connection connection = dataSource.getConnection()) {
        String query = "SELECT timer_config, class_method_name FROM md_timer_config";
        try (PreparedStatement statement = connection.prepareStatement(query);
             ResultSet resultSet = statement.executeQuery()) {
            while (resultSet.next()) {
                String timerConfig = resultSet.getString("timer_config");
                String classMethodName = resultSet.getString("class_method_name");

                // 根据配置创建定时器任务
                @Scheduled(cron = timerConfig)
                public void performTask() {
                    clickHouseService.getClass().getMethod(classMethodName).invoke(clickHouseService);
                }
            }
        }
    } catch (SQLException e) {
        e.printStackTrace();
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
你帮我修改代码,读取数据库的这个配置表,并动态的执行配置表里面的定时器任务!帮我把Java代码写出来,哪里不对也帮我改造一下
  • 1

AI的回答如下:

在Spring Boot中动态创建定时任务并不像直接在类中声明@Scheduled注解那么简单,因为注解是在编译时解析的,不能动态添加或更改。为此,我们需要利用Spring的任务调度器(TaskScheduler)结合数据访问来实现动态定时任务。

以下是一个基于ThreadPoolTaskScheduler的实现示例:

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.scheduling.TaskScheduler;
import org.springframework.scheduling.Trigger;
import org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler;
import org.springframework.scheduling.support.CronTrigger;
import org.springframework.stereotype.Component;

import javax.sql.DataSource;
import java.lang.reflect.Method;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

@Component
public class DynamicTaskScheduler {

    @Autowired
    private DataSource dataSource;

    @Autowired
    private ApplicationContext applicationContext; // 用于获取Bean

    private TaskScheduler taskScheduler = new ThreadPoolTaskScheduler();

    @PostConstruct
    public void init() {
        taskScheduler.initialize(); // 初始化任务调度器
        loadAndScheduleTasks();
    }

    private void loadAndScheduleTasks() {
        try (Connection connection = dataSource.getConnection()) {
            String query = "SELECT timer_config, class_method_name FROM md_timer_config";
            try (PreparedStatement statement = connection.prepareStatement(query);
                 ResultSet resultSet = statement.executeQuery()) {
                while (resultSet.next()) {
                    String timerConfig = resultSet.getString("timer_config");
                    String classMethodName = resultSet.getString("class_method_name");

                    scheduleTask(timerConfig, classMethodName);
                }
            }
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    private void scheduleTask(String timerConfig, String classMethodName) {
        Class<?> serviceClass = getBeanClassByName(classMethodName.split("\\.")[0]);
        String methodName = classMethodName.substring(classMethodName.indexOf(".") + 1);

        Method method = findMethod(serviceClass, methodName);
        if (method == null) {
            throw new RuntimeException("无法找到方法: " + methodName);
        }

        Trigger trigger = new CronTrigger(timerConfig);
        taskScheduler.schedule(() -> invokeMethod(method, applicationContext.getBean(serviceClass)), trigger);
    }

    private Class<?> getBeanClassByName(String beanName) {
        return applicationContext.getBeansOfType(Object.class).keySet()
                .stream()
                .filter(key -> key.getName().equals(beanName))
                .findFirst()
                .map(key -> key.getType())
                .orElseThrow(() -> new RuntimeException("无法找到名为" + beanName + "的Bean"));
    }

    private Method findMethod(Class<?> clazz, String methodName) {
        try {
            return clazz.getMethod(methodName);
        } catch (NoSuchMethodException e) {
            return null;
        }
    }

    private void invokeMethod(Method method, Object target) {
        try {
            method.invoke(target);
        } catch (IllegalAccessException | InvocationTargetException e) {
            e.printStackTrace();
        }
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89

在这个例子中,我们首先初始化了一个ThreadPoolTaskScheduler,然后从数据库中读取定时任务配置,并为每个配置创建一个新的定时任务,这些任务通过触发器(如CronTrigger)和任务执行体(即调用指定类的方法)来定义。

需要注意的是,getBeanClassByName方法是基于假设数据库中的类名与Spring容器中的Bean名称一致,如果实际情况不同,可能需要调整这个方法以适应实际的Bean查找逻辑。同时,findMethod方法是简单查找无参的公共方法,如果方法带有参数,还需要进一步完善该方法。

然后我们把代码复制到自己的项目跑跑改改,发现了有一个方法是错误的!
针对错误的方法,把提问的范围缩小!你要说出你自己具体的那个方法,什么问题,什么需求!

训练AI口令步骤三

上部分代码也粘贴给AI

上面代码中的getBeanClassByName方法报错,帮我重新写一个
  • 1

注意:代码一定要附在上面,要不然AI读不懂!读不懂,他的回答就会千奇百怪!你要引导它给你最佳最准的答案!
在这里插入图片描述

AI回答如下:

在Spring中,获取Bean的类型通常不是基于Bean的名称而是基于类类型。如果你的class_method_name字段格式是“ClassName.methodName”,那么我们可以尝试按类名直接获取Bean。不过,Spring容器中的Bean默认名称通常是首字母小写的类名。如果Bean的名称与类名不一致,你需要在配置文件中为Bean提供明确的名称。这里给出一个改进后的getBeanClassByName方法,假设Spring Bean的名字和类名一致:

private Class<?> getBeanClassByName(String className) {
    Map<String, Object> beans = applicationContext.getBeansWithAnnotation(Component.class);
    for (Map.Entry<String, Object> entry : beans.entrySet()) {
        if (entry.getValue().getClass().getSimpleName().equals(className)) {
            return entry.getValue().getClass();
        }
    }
    throw new RuntimeException("无法找到名为" + className + "的Bean");
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9

然而,这种方法仍然存在一定的局限性,因为它是基于类的简单名匹配,并且依赖于所有的Spring Bean都有@Component注解。在大型项目中,推荐使用更精确的方式来获取Bean,例如:

private Class<?> getBeanClassByName(String className) {
    try {
        return Class.forName(className);
    } catch (ClassNotFoundException e) {
        // 如果你想基于Spring容器中已注册的Bean名称来查找,则可以尝试以下方式
        for (String beanName : applicationContext.getBeanDefinitionNames()) {
            Class<?> beanType = applicationContext.getType(beanName);
            if (beanType.getSimpleName().equals(className)) {
                return beanType;
            }
        }
        throw new RuntimeException("无法找到名为" + className + "的Bean");
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14

请注意,尽管如此,这种方式仍不够健壮,因为在实际项目中类名和Bean名称可能存在差异。若要在Spring容器中准确地根据类名获取Bean,请确保你有足够的上下文信息来正确识别对应的Bean。如果Bean的名称和类名没有直接关系,可能需要在数据库中存储额外的信息,例如Bean的名称或者类的全限定名。
在这里插入图片描述

再把改造后的方法,放到自己项目里面测试一下跑通了!

在这里插入图片描述

最终整合AI跑通的代码如下:

package com.nasen.schedule;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.ApplicationContext;
import org.springframework.scheduling.TaskScheduler;
import org.springframework.scheduling.Trigger;
import org.springframework.scheduling.concurrent.ExecutorConfigurationSupport;
import org.springframework.scheduling.concurrent.ThreadPoolTaskScheduler;
import org.springframework.scheduling.support.CronTrigger;
import org.springframework.stereotype.Component;

import javax.annotation.PostConstruct;
import javax.sql.DataSource;
import java.lang.reflect.Method;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

@Component
public class DynamicTaskScheduler {

    @Autowired
    private DataSource dataSource;

    @Autowired
    private ApplicationContext applicationContext; // 用于获取Bean

    private TaskScheduler taskScheduler = new ThreadPoolTaskScheduler();

    @PostConstruct
    public void init() {
        ((ExecutorConfigurationSupport) taskScheduler).initialize(); // 初始化任务调度器
        loadAndScheduleTasks();
    }

    private void loadAndScheduleTasks() {
        try (Connection connection = dataSource.getConnection()) {
            String query = "SELECT timer_config, class_method_name FROM timer_config";
            try (PreparedStatement statement = connection.prepareStatement(query);
                 ResultSet resultSet = statement.executeQuery()) {
                while (resultSet.next()) {
                    String timerConfig = resultSet.getString("timer_config");
                    String classMethodName = resultSet.getString("class_method_name");

                    scheduleTask(timerConfig, classMethodName);
                }
            }
        } catch (SQLException e) {
            e.printStackTrace();
        }
    }

    private void scheduleTask(String timerConfig, String classMethodName) {
        Class<?> serviceClass = getBeanClassByName(classMethodName.split("\\.")[0]);
        String methodName = classMethodName.substring(classMethodName.indexOf(".") + 1);

        Method method = findMethod(serviceClass, methodName);
        if (method == null) {
            throw new RuntimeException("无法找到方法: " + methodName);
        }

        Trigger trigger = new CronTrigger(timerConfig);
        taskScheduler.schedule(() -> invokeMethod(method, applicationContext.getBean(serviceClass)), trigger);
    }

    private Class<?> getBeanClassByName(String className) {
        try {
            return Class.forName(className);
        } catch (ClassNotFoundException e) {
            // 如果你想基于Spring容器中已注册的Bean名称来查找,则可以尝试以下方式
            for (String beanName : applicationContext.getBeanDefinitionNames()) {
                Class<?> beanType = applicationContext.getType(beanName);
                if (beanType.getSimpleName().equals(className)) {
                    return beanType;
                }
            }
            throw new RuntimeException("无法找到名为" + className + "的Bean");
        }
    }

    private Method findMethod(Class<?> clazz, String methodName) {
        try {
            return clazz.getMethod(methodName);
        } catch (NoSuchMethodException e) {
            return null;
        }
    }

    private void invokeMethod(Method method, Object target) {
        try {
            method.invoke(target);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99

四、总结

引导思路方法很重要,你要给AI比较具体的例子,然后再缩小范围,然后再提出具体的需求,当然过程中还得自己去测代码,前提是你也得懂代码,你是一个引导者!
笔者这次用的2个AI平台互相引导,用到”豆包“与”通义千问“!
先问豆包AI,看他回答的怎么样,回答的不好,再问通义千问AI,看看是不是回答的更好!然后2者截取最好的,再引导,从这个实际例子中看,通义千问AI的训练水平更高,更聪明,更高说通义千问AI的训练程度更强!

豆包AI是字节跳动公司研发的一种人工智能工具,它基于云雀模型运行。这款工具融合了聊天机器人、写作助手和英语学习助手的功能,能应对各种任务,例如解答用户问题、进行对话、协助文本创作以及提供语言学习指导。豆包AI不仅可以从网页端访问,也能在iOS和Android平台上使用。

https://www.doubao.com/
  • 1

通义千问是阿里云研发的超大规模语言模型,能够回答问题、创作文字,还能表达观点、撰写代码,功能强大且应用场景广泛。作为一个AI助手,通义千问能够帮助用户在工作、学习、生活中提高效率与质量,通过自然语言理解和生成技术,为用户提供精准、详尽和个性化的服务。您可以通过与通义千问互动,体验其多种功能和智能特性。

https://tongyi.aliyun.com/
  • 1

2个AI 2个人工智能大师,看看他们谁强谁弱,我是让他们2个一起帮我工作!互相引导!互相帮助!

AI人工智能是什么

人工智能把它看成是一个巨大的无限的机器人或者是巨型的知识库,它能是模拟人类的神经大脑的一个创造的巨大的机器人,它可以通过自主学习与训练变得知识变得越来越丰富!我们普通人就帮它看成一个机器人即可!这个机器人可以协助你帮助你做一些工作、生活的事情,你要指导它、训练它让它为你所用!我们都看过施瓦辛格《未来战士》的天网,AI类似于天网的概念!你可能从脑子里想象你可以给他对话,他是你的管家!很多电影都有类似这些场景!笔者主要是从实际运用出发!就是生活中我们怎么运用到人工智能!

https://tongyi.aliyun.com/qianwen/
  • 1

在这里插入图片描述
在这里插入图片描述

https://www.doubao.com/
  • 1

在这里插入图片描述

五、笔者简介

国内某一线知名软件公司企业认证在职员工:任JAVA高级研发工程师,大数据领域专家,数据库领域专家兼任高级DBA!10年软件开发经验!现任国内某大型软件公司大数据研发工程师、MySQL数据库DBA,软件架构师。直接参与设计国家级亿级别大数据项目!并维护真实企业级生产数据库300余个!紧急处理数据库生产事故上百起,挽回数据丢失所造成的灾难损失不计其数!并为某国家级大数据系统的技术方案(国家知识产权局颁布)专利权的第一专利发明人!

在这里插入图片描述

在这里插入图片描述

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/2023面试高手/article/detail/607511
推荐阅读
相关标签
  

闽ICP备14008679号