sql - 在 postgres select 查询中可以插入 ascii 十进制字符吗?

标签 sql postgresql

我需要这样的 select 语句的 o/p。

您被分配到以下项目:

  • 一个
  • B
  • C

有一些空格、特殊字符和换行符。为此,我使用了 ascii 字符 chr(10)、chr(32)、chr(8226)。 它工作正常但查询看起来不太好&我不确定这样做是否是一个好方法。 查询看起来像这样

SELECT 
'You are assigned to following projects:' || chr(10) || chr(32) || chr(8226) || chr(32) ||
string_agg(e.projects, chr(10) || chr(32) || chr(8226) || chr(32))

这是否也适用于所有操作系统和所有环境?

最佳答案

您有几个选择:

  • 按字面意思插入字符。通常是最好的选择。想要一个 ”•”?使用类似 'this is a •' 的字符串。 如果您的client_encoding 是正确的并且您使用的编码包括您想要的字符(如),则不需要更多。这是 SQL 标准。换行符可以作为文字包含在内:

    SELECT '
    ' AS "this_is_a_newline";
    

    此方法可能不适用于某些不可打印的字符,具体取决于数据库的实现。对于 PostgreSQL,它适用于除 \x00 之外的所有内容,零字节,PostgreSQL 在 text/varchar 等中根本不支持,仅在 bytea 中。

    注意确保你的文本编辑器/SQL 编辑器的文本编码与你的连接告诉 PostgreSQL client_encoding 的编码相匹配,否则你会得到损坏的字符串或奇怪的错误。类 unix 终端的用户还需要确保终端编码与 client_encoding 匹配,以避免出现奇怪的输出错误。如今,Windows 是唯一一个普遍存在此问题的平台。

  • E'' 转义字符串中通过十六进制或 unicode 文字插入字符,例如E'这是一个\u2022' 。请注意,\u 转义是十六进制的 - 0x2022 是十进制的 8226。E'' 语法是 PostgreSQL 扩展。

  • 对于定义了简写转义的字符,在转义字符串中使用简写转义,例如E'\n'。这是一个 PostgreSQL 扩展。

  • 使用 chr(8226),如您所述,但请注意 chr 根据您的 server_encoding(数据库的文本编码)。所以我鼓励它。对于多字节字符,您只会收到类似 ERROR: requested character too large for encoding: 8226:

    的错误
      regress=> CREATE DATABASE latin ENCODING 'latin-1' LC_CTYPE 'C' LC_COLLATE 'C' TEMPLATE template0;
      CREATE DATABASE
      regress=> \c latin
      You are now connected to database "latin" as user "craig".
      latin=> SHOW server_encoding;
       server_encoding 
      -----------------
       LATIN1
      (1 row)
    
      latin=> SHOW client_encoding;
       client_encoding 
      -----------------
       UTF8
      (1 row)
      latin=> select chr(8226);
      ERROR:  requested character too large for encoding: 8226
    

    但是对于序号在 1 字节范围内的字符,您可能会得到一个意想不到的字符。以 ü 为例,它在 utf-8 和 latin-1 (iso-8859-1) 中都是 0xfc(十进制 252),但在 iso-8859-5 中是 ќ。所以:

     regress=> SHOW server_encoding;
     server_encoding 
     -----------------
     UTF8
    
     regress=> SELECT chr(252);
     chr 
     -----
      ü
    
     regress=> CREATE DATABASE iso5 ENCODING 'iso-8859-5' LC_CTYPE 'C' LC_COLLATE 'C' TEMPLATE template0;
    
     regress=> \c iso5
    
     iso5=> SELECT chr(252);
     chr 
    -----
     ќ
    

所以我的建议是:尽可能使用文字。在必须使用转义符的地方,使用带有 unicode 转义符的 E'' 字符串,以防止基于当前服务器编码的代码点含义出现歧义。避免 \x 转义和 chr

对于你写的具体例子,你应该使用:

SELECT 'You are assigned to following projects:

    • A
    • B
    • C';

使用非常旧的 PostgreSQL 版本的读者请注意:非常旧的 PostgreSQL 版本不支持 E'' 字符串并将所有字符串视为转义字符串。所以 '\n' 表示“换行符”,而现代 PostgreSQL 遵循 SQL 标准,其中 '\n' 只是字符串“\n”。只有略微史前的版本仍然这样做,但会发出警告并让您通过设置 standard_conforming_strings = on 来请求标准行为。这是很长一段时间以来的默认设置。

关于sql - 在 postgres select 查询中可以插入 ascii 十进制字符吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24668847/

相关文章:

mysql - SQL - 如何连接两个表并根据它们之间的 ID 对列求和?

sql - 创建跨 Maven 测试阶段工作的临时数据库?

sql - 奇怪的 SQL2005 问题。 "SqlConnection does not support parallel transactions"

sql - 性能调优 PostgreSQL

通过 Windows/PuTTY 的 PostgreSQL SSH 端口转发

postgresql - 在服务器端使用 over table 计算表列

node.js - 尝试批量插入行时发生 Knexjs 错误 : Timeout acquiring a connection. 池可能已满。

mysql - 如何在sql查询之间添加一个月的第一天和最后一天?

sql - 一个SQL查询来重新排序一列的数字全为奇数,甚至全为偶数

sql - 试图修改 PostgreSQL 中的约束