【问题标题】:Impala ODBC Driver for Multiple Insert用于多次插入的 Impala ODBC 驱动程序
【发布时间】:2016-09-22 21:57:04
【问题描述】:

我在通过 odbc Impala(最新版本)进行多次插入时遇到问题。

我正在尝试在具有 4 列的 Impala 表(在 Cloudera 上)中插入 2000 行,但我收到两个错误:

[Cloudera][SQLEngine] (31580) 语句长度超过最大值:16384。 [Cloudera][ImpalaODBC] (110) 在 Impala 中执行查询时出错:[HY000] : AnalysisException: Syntax error in line 1: ...

我正在使用查询参数化查询:

INSERT INTO name_table (a,b,c,d) VALUES (?,?,?,?) , (?,?,?,?) , ....

现在我的问题是:

有没有办法使用 odbc 驱动程序插入数百万行而不使用单次插入?

谢谢。

【问题讨论】:

    标签: odbc driver impala


    【解决方案1】:

    目前,一个查询最多有 16384 个字符,这看起来应该是一个更高的限制。我们目前正在调查这个下限是否有原因。

    也就是说,通过 ODBC 插入多个值的更有效方法是使用查询:

    INSERT INTO name_table (a,b,c,d) VALUES (?,?,?,?)

    然后使用数组绑定将多个参数集绑定到您的参数。这样,驱动程序可以在内部优化执行,而不会遇到查询长度限制。你已经试过了吗?

    【讨论】:

    • 顺便说一句,即将发布的驱动程序会将限制增加到 Impala 支持的实际限制。
    • 您能否提供并举例说明如何在单个 INSERT 中插入多行?
    【解决方案2】:

    我已经尝试执行以下代码:

            OdbcCommand oComm = oConn.CreateCommand();
    
            StringBuilder sb = new StringBuilder();
    
    
            sb.AppendFormat("INSERT INTO {0}.{1} (a,b,c,d) VALUES (?,?,?,?)", dbName, tableName);
    
    
    
            List<OdbcParameter> psl = new List<OdbcParameter>(1000 * 4);
    
            for (int i = 0; i < 1000; i++)
            {
    
                var odbcParameter = new OdbcParameter();
                odbcParameter.ParameterName = "@a";
                odbcParameter.OdbcType = OdbcType.Text;
                odbcParameter.Value ="a"+i;
                psl.Add(odbcParameter);
    
                odbcParameter = new OdbcParameter();
                odbcParameter.ParameterName = "@b";
                odbcParameter.OdbcType = OdbcType.Text;
                odbcParameter.Value = "b" + i;
                psl.Add(odbcParameter);
    
                odbcParameter = new OdbcParameter();
                odbcParameter.ParameterName = "@c";
                odbcParameter.OdbcType = OdbcType.Text;
                odbcParameter.Value = "c" + i;
                psl.Add(odbcParameter);
    
                odbcParameter = new OdbcParameter();
                odbcParameter.ParameterName = "@d";
                odbcParameter.Value = "d" + i;
                odbcParameter.OdbcType = OdbcType.Text;
                psl.Add(odbcParameter);
    
    
            }
    
    
            oComm.Parameters.AddRange(psl.ToArray());
    
            oComm.CommandText = sb.ToString();
    
            oComm.executeNonQUery();
    

    最后,我的表仅由具有前四个参数值的一条记录组成。

    我的代码有问题吗?

    谢谢。

    【讨论】:

    • 不幸的是,您正在使用 ADO.NET Provider for ODBC(ODBC 上的 C# 包装器),这限制了您与 ODBC API 交互的方式。如所写,您只是将一堆值添加到列表中,然后将范围设置为您的 4 个参数的整个集合,而不是使用多组 4。您是否尝试过 msdn.microsoft.com/en-us/library/aadf8fk2%28v=vs.110%29.aspx 代替?
    • 我尝试使用 OdbcDataAdapter,但 odbc 为我的 DataTable 中的每一新行执行一个插入语句,性能不佳。针对我的问题的一些建议或示例?
    • 不幸的是,如果用于 ODBC 的 ADO.NET 提供程序将其转换为 ODBC 层的次优执行,那么您就不走运了。 16384 个字符的限制已被取消,并将在驱动程序的下一个版本中取消,但我不确定何时最终会为您公开。我会为此向 Cloudera 提出问题。
    • 从那以后你能解决这个问题吗?您是否有机会使用解决方案更新您的问题?
    猜你喜欢
    • 1970-01-01
    • 2016-03-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-09-28
    • 1970-01-01
    • 2016-03-16
    相关资源
    最近更新 更多