1

我对 java 中的 StringBuilder 感到困惑。我的代码在这里:

StringBuilder cmdB = new StringBuilder(
            "INSERT IGNORE INTO Query ( context, category, generality, freshness, TokenCount, type) VALUES ");
    for (int i = 0; i < querydata.size(); i++) {

        if (i == 0)
            cmdB.append("('");
        else
            cmdB.append(",('");
        cmdB.append(querydata.get(i).getContext() + "',"
                + querydata.get(i).getCategory() + ","
                + querydata.get(i).getGenerality() + ","
                + querydata.get(i).getFreshness() + ","
                + querydata.get(i).getTokenCount() + ","
                + querydata.get(i).getType());
        cmdB.append(")");
    }
    cmdB.append(";");

我有 Mysql 作为数据库,想创建插入 1000 行的字符串。querydata.get(i).getContext() 返回 String 并包含英语(left ro right)和波斯语(从右到左的语言)。

当我的 querydata.get(i).getContext() 返回“دانلود کرک بازی ghost recon”时,我的 Stringbuilder 将其合并。我的结果如下所示。

INSERT IGNORE INTO Query ( context, category, generality, freshness, TokenCount, type) VALUES ('پخش زنده فوتبال',2,1.0,0.0,2,1),('عکسهای جشنواره فیلم فجر',2,1.0,0.0, 2,1),('نتایج لیگ برتر',2,1.0,0.0,2,1),('دانلود کرک بازی ghost recon',2,1.0,0.0,2,1)。

4

2 回答 2

3

就逻辑顺序而言,字符串的内容实际上没有任何问题,据我所知,可能会让您感到困惑的是打印双向文本时的呈现方式。如果您将鼠标拖动到字符串上,您可以通过选择跳跃的方式看到正在以哪个主要方向呈现的文本运行。

如果我用换行符分隔值集,我会得到

INSERT IGNORE INTO Query ( context, category, generality, freshness, TokenCount, type) VALUES
('پخش زنده فوتبال',2,1.0,0.0,2,1),
('عکسهای جشنواره فیلم فجر',2,1.0,0.0, 2,1),
('نتایج لیگ برتر',2,1.0,0.0,2,1),
('دانلود کرک بازی ghost recon',2,1.0,0.0,2,1)。

我不确定您在浏览器中看到什么,但在我的浏览器中,它将该INSERT INTO ... VALUES行视为 LTR,然后是后续行,但不包括ghost recon主要包含 RTL 的行。这是在波斯语脚本部分周围插入了 Unicode 从左到右标记 ( U+200E) 的相同字符串,以强制将周围的引号和括号视为 LTR:

INSERT IGNORE INTO Query ( context, category, generality, freshness, TokenCount, type) VALUES
('‎پخش زنده فوتبال‎',2,1.0,0.0,2,1),
('‎عکسهای جشنواره فیلم فجر‎',2, 1.0,0.0,2,1),
('‎نتایج لیگ برتر‎',2,1.0,0.0,2,1),
('‎دانلود کرک بازی‎ ghost recon',2,1.0,0.0,2,1) .

换句话说——别担心,数据库会包含正确的东西。

但我也同意这个答案,你应该考虑使用PreparedStatement而不是用 , 构建 SQLStringBuilder来防止 SQL 注入攻击(或模糊错误),以防你的任何上下文字符串包含撇号(这种情况比你想象的更常见) .

于 2012-12-31T12:32:00.130 回答
1

我不确定您在问题中到底要问什么,但您真的应该考虑使用批量插入工具来进行如此大的插入。它在内存、速度和安全性方面会更好。查看 SpringSource 的JdbcTemplate和它的batchUpdate方法。以下是从谷歌搜索中获取的简单示例...

public void insertBatch(final List<Customer> customers){
 
  String sql = "INSERT INTO CUSTOMER " +
    "(CUST_ID, NAME, AGE) VALUES (?, ?, ?)";
 
  getJdbcTemplate().batchUpdate(sql, new BatchPreparedStatementSetter() {
 
    @Override
    public void setValues(PreparedStatement ps, int i) throws SQLException {
        Customer customer = customers.get(i);
        ps.setLong(1, customer.getCustId());
        ps.setString(2, customer.getName());
        ps.setInt(3, customer.getAge() );
    }
 
    @Override
    public int getBatchSize() {
        return customers.size();
    }
  });
}
于 2012-12-31T12:03:59.967 回答