Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/384.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 是否应该同步单例方法?_Java_Spring_Multithreading_Singleton_Spring Ioc - Fatal编程技术网

Java 是否应该同步单例方法?

Java 是否应该同步单例方法?,java,spring,multithreading,singleton,spring-ioc,Java,Spring,Multithreading,Singleton,Spring Ioc,我的web应用程序(这里没有springmvc,只有核心IOC)使用了很多原型bean,其中大多数都使用了单例daobean。由于许多不同的原型bean(来自不同的请求)可能在同一时刻使用相同的方法id dao,所以是否应该对单例daobean方法进行同步化 例如,dao方法 public void setLetterNotNew(int letterId) { final String sql = "UPDATE income SET isnew=? WHERE id=?";

我的web应用程序(这里没有springmvc,只有核心IOC)使用了很多原型bean,其中大多数都使用了单例daobean。由于许多不同的原型bean(来自不同的请求)可能在同一时刻使用相同的方法id dao,所以是否应该对单例daobean方法进行同步化

例如,dao方法

public void setLetterNotNew(int letterId) {

    final String sql = "UPDATE income SET isnew=? WHERE id=?";

    try( Connection con = HikariFactory.getConnection(); PreparedStatement ps = con.prepareStatement(sql); ) {

        ps.setInt(1, 0);
        ps.setInt(2, letterId);

        int i = ps.executeUpdate();
        if(i==0) throw new SQLException("setLetterNotNew");

    } catch (SQLException e) {
        log.error(e);
    }
}
视情况而定

正如您在评论中所写,您使用的是jdbc。JDBCAPI和do上的所有操作。因此,如果您共享JDBC连接,但您的方法不需要事务(例如,它不更新之前选择的几行数据),那么它就不需要同步


但是,如果需要事务,则必须同步此方法,或者为每个线程提供自己的JDBC连接,如下所示。要实现这一点,您每次都可以用一种方法打开新连接,或者让

取决于您更新数据库的方式。许多框架已经同步,因此您不必做任何额外的工作。检查您的文档。@markspace在这里没有任何框架。这是一个基于servlet的web应用程序。数据库正在通过standart jdbc进行更新。是的,您应该使单例的方法同步,或者至少使其在同步块之间进入数据库的部分同步。还要检查您计划如何构建和获取singleton,这样您就不会以两个实例结束。如果多个线程访问共享可变状态,则需要同步。我们不知道你的“更新数据库在这里”做什么。如果它从数据源获取连接,执行其任务并关闭连接,则不需要同步。既然您已经使用了Spring,那么您肯定应该使用它的声明性事务支持及其JDBC相关类(JdbcTemplate等)。也许你已经这样做了,但是既然你没有发布代码…@Rumal创建一个单例是Spring的任务,所以我认为我们不必担心它。我如何定义该方法是否需要事务?我更新了问题。我从池中获取连接(一个静态方法HikariFactory.getConnection()),并且连接自动关闭。我还知道Jdbc在数据库级别处理多线程。因此,所讨论的方法不包含任何状态。在这种情况下,多线程如何做错事?事实上,我认为最好的方法是使用原型来实现DAOBean,那么就不必担心多线程。如果方法不包含任何状态,那么您可以安全地使用它,而不需要将Dao更改为原型bean,也不需要同步它。如果您的语句是单个更新,则不需要任何事务。事务用于确保同时使用的多个查询处理来自数据库的相同数据。在您的情况下,只有一个语句,因此没有问题。