标签: postgresql

如何在没有“cluster”命令的排他锁和日志开销的情况下实现行集群?

CLUSTER大表上的命令可能需要很长时间,并且在运行时会阻止对表的读取和写入

我不需要按索引顺序对表中的数据进行严格排序,我只希望通常一起查询的行更有可能位于同一个数据库块中,而不是均匀地分散在表中(这是它们的分布)由于日期插入表格的方式的性质,自然有)。

它可以产生很大的不同。在下面的示例中,唯一的区别是insert有一个额外的,order by mod(g,10)以便测试数据由 预先聚类host_id。当获取一个特定host_id.

是否有某种方法可以在没有排它锁和cluster命令的日志记录开销的情况下实现这种集群?

create schema stack;
set search_path=stack;
--
create table foo(host_id integer, bar text default repeat('a',400));
insert into foo(host_id) select mod(g,10) from generate_series(1,500000) g;
create index nu_foo on foo(host_id);
explain analyze select count(bar) from foo where host_id=1;
/*
                                                            QUERY PLAN
-----------------------------------------------------------------------------------------------------------------------------------
 Aggregate  (cost=30188.66..30188.67 rows=1 width=404) (actual time=1129.858..1129.859 rows=1 loops=1)
   ->  Bitmap Heap Scan on foo  (cost=919.27..30066.46 rows=48883 width=404) (actual time=253.149..1110.013 …
Run Code Online (Sandbox Code Playgroud)

postgresql clustering postgresql-9.3

5
推荐指数
1
解决办法
986
查看次数

如果复制数据后PostgreSQL启动,数据正常吗?

我正在将 PostgreSQL 数据库(即 /var/lib/postgresql)的数据从一台服务器复制到另一台服务器。服务器是相同的,除了一个是32位,另一个是64位。我已经复制了一次数据并且PostgreSQL启动了,但是,有没有办法验证数据的完整性?

postgresql migration

5
推荐指数
1
解决办法
212
查看次数

Postgres 报告的表/数据库大小与转储大小差异很大

我对一个特定数据库的大小有一个非常奇怪的误报。

根据\l+psqlDB 大小是 292 MB。

对以下语句报告的大小进行求和也报告非常接近 292 MB。

SELECT
    table_name,
    pg_size_pretty(total_size) AS total_size
FROM (
    SELECT
        table_name,
        pg_total_relation_size(table_name) AS total_size
    FROM (
        SELECT ('"' || table_schema || '"."' || table_name || '"') AS table_name
        FROM information_schema.tables
    ) AS all_tables
    ORDER BY total_size DESC
) AS pretty_sizes
Run Code Online (Sandbox Code Playgroud)

然而pg_dump,这个数据库的一个产生了一个 2.02 GB 的 sql 文件

我怀疑这两种计数方法都会跳过 LOB,因为该数据库中有两个表包含TEXT内容较大的字段(每行最多 ~4MB)。

有没有办法在大小计算中包含 LOB?

编辑: 它变得更奇怪了:

这个查询:

SELECT SUM(LENGTH(text_column))
FROM some_table
Run Code Online (Sandbox Code Playgroud)

给出 2,091,245,318(即 2.02 GiB)的结果,大约是转储的大小。

postgresql database-size

5
推荐指数
1
解决办法
2282
查看次数

在 Windows 上构建 plpgsql_check 时出现问题

我尝试在 Windows XP 32 位和 Visual Studio 2010 上通过 @PavelStehule(Erwin Brandstetter在这个答案中向我推荐它)构建plpgsql_check 扩展(我将本文用作手册)。但是,我收到以下错误:

error LNK2001: unresolved external symbol _exec_get_datum_type
error LNK2001: unresolved external symbol _plpgsql_compile
error LNK2001: unresolved external symbol _plpgsql_build_datatype
error LNK2001: unresolved external symbol _plpgsql_stmt_typename
error LNK2001: unresolved external symbol _plpgsql_parser_setup
Run Code Online (Sandbox Code Playgroud)

此外,还有两个 IntelliSense 错误:expected a ')'在 plpgsql.h(第 923 行和第 953 行 - 都在与数据相关的函数中) - 我希望这些是错误警报(如果它们很重要,如何解决它们?)。

经过一番谷歌搜索后,我发现有人在 OS X 上遇到了类似的问题。问题是 plpgsql.so 要么没有链接,要么没有工作。我的电脑上没有 plpgsql.so,但我有 plpgsql.dll 应该对应它。所以我链接了它,错误改变了:

error LNK1107: invalid or corrupt …
Run Code Online (Sandbox Code Playgroud)

postgresql windows installation visual-studio-2010

5
推荐指数
1
解决办法
381
查看次数

针对 20 多个列的不同搜索的最佳索引策略指南

我正在运行一个汽车搜索引擎。它由 postgresql 9.3 安装支持。

现在我不确定对前端搜索进行索引优化的最佳方法/策略。

问题:

包含汽车的表包含大约 150 万行。搜索汽车的人需要不同的搜索条件。有的按品牌/型号搜索,有的按年份搜索,有的按里程搜索,有的按价格搜索,有的按特殊设备搜索,等等 - 通常他们将一大堆标准结合在一起。当然,有些,如品牌/模式和价格,比其他的使用频率更高。我们总共提供:9 个类别标准,如品牌/型号或车身类型,加上 5 个数字标准,如价格或里程数,以及 12 个布尔标准,如设备。最后,人们可以按不同的列(年份、价格、里程和我们为汽车创建的分数)对结果进行排序。默认情况下,我们按照自己生成的分数进行排序。

到目前为止我所做的:

我已经“轻松”分析了标准的使用,并创建了一些索引(10)。其中包括例如价格、里​​程和品牌/型号的组合指数。由于我们只对显示实际待售汽车的结果感兴趣,因此将索引作为销售状态列上的部分索引。

问题:

  1. 您将如何分析和确定应该对哪些列编制索引,以及如何编制?
  2. 为 20 多个列上发生的搜索优化索引时,最佳策略是什么,其中使用和组合变化很大?(只对所有内容进行索引,对某些列进行索引,进行组合索引,仅进行单列索引等)
  3. 我希望索引所有列没有意义?
  4. 我希望索引布尔列没有意义?
  5. 是否对 5 个常用列进行组合索引而不是对每个列进行单独索引更好?
  6. 按我的默认排序对所有索引进行排序是个好主意吗?
  7. 您是否有使用其他可以大大提高性能的方法(例如,强制索引保留在内存中等)的经验?

postgresql performance index index-tuning

5
推荐指数
1
解决办法
293
查看次数

如果所选列为空,则返回 group by 中的默认值

我正在尝试运行一个工作正常的 group by 语句,但是,其中一个“组”为空。如何为该行返回“未知”?

例如:

    10000
A   9999
B   9990
C   4
Run Code Online (Sandbox Code Playgroud)

等等。

第一行我想在查询中作为“未知”返回。

postgresql null group-by

5
推荐指数
1
解决办法
5280
查看次数

PostgreSQL 似乎忽略了 CTE 中的 RAISE EXCEPTION

使用 PostgreSQL 9.3 我一直在尝试定义一个assert辅助函数来检查空查询结果和类似的事情,如下所示:

CREATE FUNCTION public.assert (
    in_assertion boolean,
    in_errormessage text
)
RETURNS boolean
IMMUTABLE
LANGUAGE plpgsql
SECURITY INVOKER
AS $function$
    BEGIN
        IF NOT in_assertion THEN
            RAISE EXCEPTION 'assertion failed: %', in_errormessage;
        END IF;

        RETURN in_assertion;
    END;
$function$
;
Run Code Online (Sandbox Code Playgroud)

经过测试,我发现异常没有像我期望的那样抛出。例如,对于CREATE TABLE emptytable (somecolumn text);

CREATE FUNCTION public.testassert_buggy (
    out somevalue text
)
LANGUAGE sql
SECURITY DEFINER
AS $function$
    WITH firstquery AS (
            SELECT * FROM emptytable
    ), nonemptycheck AS (
            SELECT assert(count(*) = 42, 'nonemptycheck …
Run Code Online (Sandbox Code Playgroud)

postgresql cte

5
推荐指数
1
解决办法
1622
查看次数

用于在 JSON 数组中查找属性组合的索引

基于这个关于 SO 的相关问题

如果您只想要简单的匹配,这很好用。假设在 JSON 数据中tracks同时具有ArtistTitle字段。所以我们有类似的东西:

INSERT INTO tracks (id, data)
VALUES (1, '[{"artist": "Simple Plan", "title": "Welcome to My Life"}]');
Run Code Online (Sandbox Code Playgroud)

我们像在原始问题中一样创建索引:

CREATE INDEX tracks_artists_gin_idx ON tracks
USING GIN (json2arr(data, 'artist'));

CREATE INDEX tracks_title_gin_idx ON tracks
USING GIN (json2arr(data, 'title'));
Run Code Online (Sandbox Code Playgroud)

所以现在我们有两个字段要匹配。如您所见,如果我们执行以下原始查询(经过非常简单的修改):

SELECT *
FROM   tracks
WHERE  '{"ARTIST NAME"}'::text[] <@ (json2arr(data, 'artist'))
AND    '{"TITLE"}'::text[]       <@ (json2arr(data, 'title'))
Run Code Online (Sandbox Code Playgroud)

这将给出错误的答案,因为 JSON 数组中的艺术家和标题数组的索引不必匹配此查询以匹配 JSON 中的某些内容。执行此查询的正确方法是什么,以便我们可以获得所需的精确匹配?是否json2arr()需要改变?

编辑:为什么这是错误的

假设我们的表有如下记录:

INSERT INTO tracks (id, data) …
Run Code Online (Sandbox Code Playgroud)

postgresql index array json

5
推荐指数
1
解决办法
3504
查看次数

以某些字符为前缀的自动增量字符变化列

我在 PostgreSQL 中有一个用于医院患者的表,我想将它的主键设置为PAT0000001( char varying) 并将该字段保持为自动增量

有没有办法实现这一目标?

postgresql database-design auto-increment postgresql-9.2

5
推荐指数
1
解决办法
1万
查看次数

使用多线程时,重复键违反了唯一约束

我正在使用 ExecutorService,其固定线程池为 50,固定数据库连接池为 50,使用 HikariCP。每个工作线程处理一个数据包(一个“报告”),检查它是否有效(其中每个报告必须有唯一的unit_id、时间、纬度和经度),从连接池中抓取一个db连接,然后将报告插入报告表。唯一性约束是用 postgresql 创建的,称为“reports_uniqueness_index”。当我的音量很大时,我会收到大量以下错误:

org.postgresql.util.PSQLException: ERROR: duplicate key value 
  violates unique constraint "reports_uniqueness_index"
Run Code Online (Sandbox Code Playgroud)

这就是我认为的问题所在。在插入数据库之前,我执行检查以确定表中是否已存在具有相同unit_id、时间、纬度和经度的报告。如果不是,那么报告是有效的,我执行插入。但是,我认为因为我使用并发,所以我有 50 个线程同时检查报告是否有效,并且由于尚未插入它们中的任何一个,每个线程都认为它具有有效的报告以及何时将它们插入同一时刻,也就是 postgresql 引发错误的时候。

我想要一个不会因并发而产生任何延迟的解决方案。我一直试图避免使用同步语句或重入锁,因为数据库插入需要尽快发生。这是这里的插入:

 private boolean save(){
        Connection conn=null;
        Statement stmt=null;
        int status=0;
        DbConnectionPool dbPool = DbConnectionPool.getInstance();
        String sql = = "INSERT INTO reports"
        sql += " (unit_id, time, time_secs, latitude, longitude, speed, created_at)";
        sql += " values (...)";
        try {
            conn = dbPool.getConnection();
            stmt = conn.createStatement();
            status = stmt.executeUpdate(sql);
        } catch (SQLException e) {
            return false;
        } finally {
            try { …
Run Code Online (Sandbox Code Playgroud)

postgresql java

5
推荐指数
1
解决办法
2万
查看次数