【问题标题】:PostgreSQL: Can't use DISTINCT for some data typesPostgreSQL:不能对某些数据类型使用 DISTINCT
【发布时间】:2010-06-27 09:14:12
【问题描述】:

我有一个名为_sample_table_delme_data_files 的表,其中包含一些重复项。我想将其记录复制到data_files

INSERT INTO data_files (SELECT distinct * FROM _sample_table_delme_data_files);
ERROR:  could not identify an ordering operator for type box3d
HINT:  Use an explicit ordering operator or modify the query.

问题是,PostgreSQL 无法比较(或排序)box3d 类型。如何提供这样的排序运算符,以便我只能将不同的值放入目标表中?

提前致谢,

亚当

【问题讨论】:

    标签: postgresql postgis comparator


    【解决方案1】:

    如果您不添加运算符,您可以尝试使用其输出函数将box3d 数据转换为文本,例如:

    INSERT INTO data_files (SELECT distinct othercols,box3dout(box3dcol) FROM _sample_table_delme_data_files);
    

    编辑下一步是:将其转换回box3d

    INSERT INTO data_files SELECT othercols, box3din(b) FROM (SELECT distinct othercols,box3dout(box3dcol) AS b FROM _sample_table_delme_data_files);
    

    (我的系统上没有box3d,因此未经测试。)

    【讨论】:

      【解决方案2】:

      数据类型 box3d 没有用于 DISTINCT 操作的运算符。你必须create the operator,或者问PostGIS-project,也许有人已经解决了这个问题。

      【讨论】:

        【解决方案3】:

        最后被同事解决了。

        让我们看看有多少重复:

        SELECT COUNT(*) FROM _sample_table_delme_data_files ;
         count                                                               
        -------                                                              
         12728                                                               
        (1 row)
        

        现在,我们将在源表中添加另一列,以帮助我们区分相似的行:

        ALTER TABLE _sample_table_delme_data_files ADD COLUMN id2 serial;
        

        我们现在可以看到 dups:

        SELECT id, id2 FROM _sample_table_delme_data_files ORDER BY id LIMIT 10;
           id   | id2                                                                           
        --------+------                                                                         
         198748 | 6449                                                                          
         198748 |   85                                                                          
         198801 |  166                                                                          
         198801 | 6530                                                                          
         198829 |   87                                                                          
         198829 | 6451                                                                          
         198926 |   88                                                                          
         198926 | 6452                                                                          
         199062 | 6532                                                                          
         199062 |  168                                                                          
        (10 rows)       
        

        并删除它们:

        DELETE FROM _sample_table_delme_data_files 
            WHERE id2 IN (SELECT max(id2) FROM _sample_table_delme_data_files 
                                 GROUP BY id 
                                       HAVING COUNT(*)>1);
        

        让我们看看它是否有效:

        SELECT id FROM _sample_table_delme_data_files GROUP BY id HAVING COUNT(*)>1;
         id
        ----
        (0 rows)
        

        删除辅助列:

        ALTER TABLE _sample_table_delme_data_files DROP COLUMN id2;
        ALTER TABLE
        

        将剩余的行插入到目标表中:

        INSERT INTO data_files (SELECT * FROM _sample_table_delme_data_files);
        INSERT 0 6364
        

        【讨论】:

        • 所以实际上您只需要区分“id”列而不是所有列(包括几何列)?如果您在问题中进行了解释,那将对答案产生很大影响。
        • 你说得对,这就是我将@Edmund 的答案标记为正确答案的原因;我希望这也能有所帮助。
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2017-12-14
        • 1970-01-01
        • 1970-01-01
        • 2018-02-24
        • 2018-03-04
        相关资源
        最近更新 更多