Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/344.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 通过随机选取表来执行SELECTSQL_Java_Database_Multithreading_Random_Executorservice - Fatal编程技术网

Java 通过随机选取表来执行SELECTSQL

Java 通过随机选取表来执行SELECTSQL,java,database,multithreading,random,executorservice,Java,Database,Multithreading,Random,Executorservice,我正在从事一个项目,在该项目中,我在不同的数据库中有两个具有不同模式的表。这意味着我有两个不同的连接参数用于使用JDBC连接这两个表- 假设下面是config.property文件- TABLES: table1 table2 #For Table1 table1.url: jdbc:mysql://localhost:3306/garden table1.user: gardener table1.password: shavel table1.driver: jdbc-driver tab

我正在从事一个项目,在该项目中,我在不同的数据库中有两个具有不同模式的表。这意味着我有两个不同的连接参数用于使用JDBC连接这两个表-

假设下面是
config.property
文件-

TABLES: table1 table2

#For Table1
table1.url: jdbc:mysql://localhost:3306/garden
table1.user: gardener
table1.password: shavel
table1.driver: jdbc-driver
table1.percentage: 80



#For Table2
table2.url: jdbc:mysql://otherhost:3306/forest
table2.user: forester
table2.password: axe
table2.driver: jdbc-driver
table2.percentage: 20
下面的方法将读取上面的
config.property文件
,并为每个表创建一个
ReadTableConnectionInfo对象

private static HashMap<String, ReadTableConnectionInfo> tableList = new HashMap<String, ReadTableConnectionInfo>();

private static void readPropertyFile() throws IOException {

    prop.load(Read.class.getClassLoader().getResourceAsStream("config.properties"));

    tableNames = Arrays.asList(prop.getProperty("TABLES").split(" "));

    for (String arg : tableNames) {

        ReadTableConnectionInfo ci = new ReadTableConnectionInfo();

        String url = prop.getProperty(arg + ".url");
        String user = prop.getProperty(arg + ".user");
        String password = prop.getProperty(arg + ".password");
        String driver = prop.getProperty(arg + ".driver");
        double percentage = Double.parseDouble(prop.getProperty(arg + ".percentage"));

        ci.setUrl(url);
        ci.setUser(user);
        ci.setPassword(password);
        ci.setDriver(driver);
        ci.setPercentage(percentage);

        tableList.put(arg, ci);
    }

}
现在,我正在为指定数量的线程创建ExecutorService,并将这个
tableList对象
传递给
ReadTask
类的构造函数-

        // create thread pool with given size
        ExecutorService service = Executors.newFixedThreadPool(10);

        for (int i = 0; i < 10; i++) {
            service.submit(new ReadTask(tableList));
        }
目前我有两个表,这意味着每个线程将为每个表建立两个连接,然后根据随机生成数使用特定的表连接在该表上执行SELECT*

算法:-

class ReadTask implements Runnable {

    private Connection[] dbConnection = null;
    private ConcurrentHashMap<ReadTableConnectionInfo, Connection> tableStatement = new ConcurrentHashMap<ReadTableConnectionInfo, Connection>();

    public ReadTask(LinkedHashMap<String, XMPReadTableConnectionInfo> tableList) {
        this.tableLists = tableList;
    }


    @Override
    public run() {

    int j = 0;
    dbConnection = new Connection[tableLists.size()];

    //loop around the map values and make the connection list
    for (ReadTableConnectionInfo ci : tableLists.values()) {

    dbConnection[j] = getDBConnection(ci.getUrl(), ci.getUser(), ci.getPassword(), ci.getDriver());
    tableStatement.putIfAbsent(ci, dbConnection[j]);

    j++;
    }

      Random random = new SecureRandom();

      while ( < 60 minutes) {

        double randomNumber = random.nextDouble() * 100.0;
        ReadTableConnectionInfo table = selectRandomConnection(randomNumber);

        for (Map.Entry<ReadTableConnectionInfo, Connection> entry : tableStatement.entrySet()) {

            if (entry.getKey().getTableName().equals(table.getTableName())) {

                final String id = generateRandomId(random);
                final String selectSql = generateRandomSQL(table);

                preparedStatement = entry.getValue().prepareCall(selectSql);
                preparedStatement.setString(1, id);

                rs = preparedStatement.executeQuery();
            }
        }
      }
    }



        private String generateRandomSQL(ReadTableConnectionInfo table) {

        int rNumber = random.nextInt(table.getColumns().size());

        List<String> shuffledColumns = new ArrayList<String>(table.getColumns());
        Collections.shuffle(shuffledColumns);

        String columnsList = "";

        for (int i = 0; i < rNumber; i++) {
            columnsList += ("," + shuffledColumns.get(i));
        }

        final String sql = "SELECT ID" + columnsList + "  from "
                + table.getTableName() + " where id = ?";

        return sql;
    }


    private ReadTableConnectionInfo selectRandomConnection(double randomNumber) {

        double limit = 0;
        for (ReadTableConnectionInfo ci : tableLists.values()) {
            limit += ci.getPercentage();
            if (random.nextDouble() < limit) {
                return ci;
            }
            throw new IllegalStateException();
        }
        return null;
    }
    }
  • 生成1到100之间的随机数
  • 如果该随机数小于
    table1.getPercentage()
    ,则选择
    table1
    然后使用
    table1语句对象
    对该数据库进行
    selectsql调用
  • 否则,请选择
    table2
    ,然后使用
    table2语句对象
    对该数据库进行
    selectsql调用
  • 我的问题-

    class ReadTask implements Runnable {
    
        private Connection[] dbConnection = null;
        private ConcurrentHashMap<ReadTableConnectionInfo, Connection> tableStatement = new ConcurrentHashMap<ReadTableConnectionInfo, Connection>();
    
        public ReadTask(LinkedHashMap<String, XMPReadTableConnectionInfo> tableList) {
            this.tableLists = tableList;
        }
    
    
        @Override
        public run() {
    
        int j = 0;
        dbConnection = new Connection[tableLists.size()];
    
        //loop around the map values and make the connection list
        for (ReadTableConnectionInfo ci : tableLists.values()) {
    
        dbConnection[j] = getDBConnection(ci.getUrl(), ci.getUser(), ci.getPassword(), ci.getDriver());
        tableStatement.putIfAbsent(ci, dbConnection[j]);
    
        j++;
        }
    
          Random random = new SecureRandom();
    
          while ( < 60 minutes) {
    
            double randomNumber = random.nextDouble() * 100.0;
            ReadTableConnectionInfo table = selectRandomConnection(randomNumber);
    
            for (Map.Entry<ReadTableConnectionInfo, Connection> entry : tableStatement.entrySet()) {
    
                if (entry.getKey().getTableName().equals(table.getTableName())) {
    
                    final String id = generateRandomId(random);
                    final String selectSql = generateRandomSQL(table);
    
                    preparedStatement = entry.getValue().prepareCall(selectSql);
                    preparedStatement.setString(1, id);
    
                    rs = preparedStatement.executeQuery();
                }
            }
          }
        }
    
    
    
            private String generateRandomSQL(ReadTableConnectionInfo table) {
    
            int rNumber = random.nextInt(table.getColumns().size());
    
            List<String> shuffledColumns = new ArrayList<String>(table.getColumns());
            Collections.shuffle(shuffledColumns);
    
            String columnsList = "";
    
            for (int i = 0; i < rNumber; i++) {
                columnsList += ("," + shuffledColumns.get(i));
            }
    
            final String sql = "SELECT ID" + columnsList + "  from "
                    + table.getTableName() + " where id = ?";
    
            return sql;
        }
    
    
        private ReadTableConnectionInfo selectRandomConnection(double randomNumber) {
    
            double limit = 0;
            for (ReadTableConnectionInfo ci : tableLists.values()) {
                limit += ci.getPercentage();
                if (random.nextDouble() < limit) {
                    return ci;
                }
                throw new IllegalStateException();
            }
            return null;
        }
        }
    
    我很难弄清楚应该如何应用上述算法,我应该如何比较
    随机数
    与每个
    表的百分比
    ,然后决定需要使用哪个表,然后弄清楚需要使用哪个
    表连接和语句
    来进行
    选择sql呼叫

    这意味着我需要检查每个表的
    getPercentage()
    方法,并将它们与随机数进行比较

    现在我只有两个表,将来我可以有三个表,百分比分布可能为
    8010

    更新:-

    class ReadTask implements Runnable {
    
        private Connection[] dbConnection = null;
        private ConcurrentHashMap<ReadTableConnectionInfo, Connection> tableStatement = new ConcurrentHashMap<ReadTableConnectionInfo, Connection>();
    
        public ReadTask(LinkedHashMap<String, XMPReadTableConnectionInfo> tableList) {
            this.tableLists = tableList;
        }
    
    
        @Override
        public run() {
    
        int j = 0;
        dbConnection = new Connection[tableLists.size()];
    
        //loop around the map values and make the connection list
        for (ReadTableConnectionInfo ci : tableLists.values()) {
    
        dbConnection[j] = getDBConnection(ci.getUrl(), ci.getUser(), ci.getPassword(), ci.getDriver());
        tableStatement.putIfAbsent(ci, dbConnection[j]);
    
        j++;
        }
    
          Random random = new SecureRandom();
    
          while ( < 60 minutes) {
    
            double randomNumber = random.nextDouble() * 100.0;
            ReadTableConnectionInfo table = selectRandomConnection(randomNumber);
    
            for (Map.Entry<ReadTableConnectionInfo, Connection> entry : tableStatement.entrySet()) {
    
                if (entry.getKey().getTableName().equals(table.getTableName())) {
    
                    final String id = generateRandomId(random);
                    final String selectSql = generateRandomSQL(table);
    
                    preparedStatement = entry.getValue().prepareCall(selectSql);
                    preparedStatement.setString(1, id);
    
                    rs = preparedStatement.executeQuery();
                }
            }
          }
        }
    
    
    
            private String generateRandomSQL(ReadTableConnectionInfo table) {
    
            int rNumber = random.nextInt(table.getColumns().size());
    
            List<String> shuffledColumns = new ArrayList<String>(table.getColumns());
            Collections.shuffle(shuffledColumns);
    
            String columnsList = "";
    
            for (int i = 0; i < rNumber; i++) {
                columnsList += ("," + shuffledColumns.get(i));
            }
    
            final String sql = "SELECT ID" + columnsList + "  from "
                    + table.getTableName() + " where id = ?";
    
            return sql;
        }
    
    
        private ReadTableConnectionInfo selectRandomConnection(double randomNumber) {
    
            double limit = 0;
            for (ReadTableConnectionInfo ci : tableLists.values()) {
                limit += ci.getPercentage();
                if (random.nextDouble() < limit) {
                    return ci;
                }
                throw new IllegalStateException();
            }
            return null;
        }
        }
    
    class ReadTask实现可运行{
    私有连接[]dbConnection=null;
    私有ConcurrentHashMap tableStatement=新ConcurrentHashMap();
    公共读取任务(LinkedHashMap表列表){
    this.tableList=tableList;
    }
    @凌驾
    公营{
    int j=0;
    dbConnection=新连接[tableLists.size()];
    //循环映射值并创建连接列表
    对于(ReadTableConnectionInfo ci:TableList.values()){
    dbConnection[j]=getDBConnection(ci.getUrl(),ci.getUser(),ci.getPassword(),ci.getDriver());
    表statement.putIfAbsent(ci,dbConnection[j]);
    j++;
    }
    Random Random=新的SecureRandom();
    而(<60分钟){
    双随机数=random.nextDouble()*100.0;
    ReadTableConnectionInfo table=选择随机连接(随机数);
    for(Map.Entry:tableStatement.entrySet()){
    if(entry.getKey().getTableName().equals(table.getTableName())){
    最终字符串id=GeneratorDomain(随机);
    最终字符串selectSql=generateRandomSQL(表);
    preparedStatement=entry.getValue().prepareCall(选择SQL);
    准备好的报表。设置字符串(1,id);
    rs=preparedStatement.executeQuery();
    }
    }
    }
    }
    私有字符串生成器SQL(ReadTableConnectionInfo表){
    int rNumber=random.nextInt(table.getColumns().size());
    List shuffledColumns=newarraylist(table.getColumns());
    Collections.shuffle(shuffledColumns);
    字符串columnsList=“”;
    for(int i=0;i
    无论您有多少个表,它们的百分比总和始终为100。概念化选择方式的最简单方法是将每个表视为代表一个百分比范围

    例如,有三个表包含您提到的百分比(80%、10%、10%),您可以将它们概念化为:

    随机数 From To==表== 0.0000 0.8000表1 0.8000 0.9000表2 0.9000 1.0000表3

    因此,生成一个介于0.0000和1.0000之间的随机#,然后沿着有序列表,查看哪个范围合适,因此使用哪个表


    (顺便说一句:我不知道为什么每个表都有两个连接。)

    不管有多少个表,它们的百分比加起来总是100。概念化选择方式的最简单方法是将每个表视为代表一个百分比范围

    例如,有三个表包含您提到的百分比(80%、10%、10%),您可以将它们概念化为:

    随机数 From To==表== 0.0000 0.8000表1 0.8000 0.9000表2 0.9000 1.0000表3

    因此,生成一个介于0.0000和1.0000之间的随机#,然后沿着有序列表,查看哪个范围合适,因此使用哪个表


    (顺便说一句:我不知道为什么每个表有两个连接。)

    您可以将其视为可用连接上的一个循环,如下所示:

    public run() {
      ...
      Random random = new SecureRandom();
    
      while ( < 60 minutes) {
        double randomNumber = random.nextDouble() * 100.0;
        ReadTableConnectionInfo tableInfo = selectRandomConnection(randomNumber);
    
        // do query...
      }
    }
    
    
    private ReadTableConnectionInfo selectRandomConnection(double randomNumber) {
      double limit = 0;
      for (ReadTableConnectionInfo ci : tableLists.values()) {
        limit += ci.getPercentage();
        if (randomNumber < limit) {
          return ci;
      }
      throw new IllegalStateException();
    }
    
    public run(){
    ...
    Random Random=新的SecureRandom();
    而(<60分钟){
    双随机数=random.nextDouble()*100.0;
    ReadTableConnectionInfo tableInfo=选择随机连接(随机编号
    
    class LookupTable {
        private int[]    weights;
        private String[] tables;
        private int      size = 0;
    
        public LookupTable(int n) {
            this.weights = new int[n];
            this.tables = new String[n];
        }
    
        public void addTable(String tableName, int r) {
            this.weights[size] = r;
            this.tables[size] = tableName;
            size++;
        }
    
        public String lookupTable(int n) {
            for (int i = 0; i < this.size; i++) {
                if (this.weights[i] >= n) {
                    return this.tables[i];
                }
            }
            return null;
        }
    }
    
        LookupTable tr = new LookupTable(3);
        // make sure adds the range from lower to upper!
        tr.addTable("table1", 20);
        tr.addTable("table2", 80);
        tr.addTable("table3", 100);
    
        Random r = new Random(System.currentTimeMillis());
        for (int i = 0; i < 10; i++) {
            // r.nextInt(101) + 1 would return a number of range [1~100]. 
            int n = r.nextInt(101) + 1;
            String tableName = tr.lookupTable(n);
            System.out.println(n + ":" + tableName);
        }