用于编码“UTF8”的无效字节序列
我试图导入一些数据到我的数据库。 所以我创build了一个临时表,
create temporary table tmp(pc varchar(10), lat decimal(18,12), lon decimal(18,12), city varchar(100), prov varchar(2));
现在我试图导入数据 ,
copy tmp from '/home/mark/Desktop/Canada.csv' delimiter ',' csv
但是,然后我得到的错误,
ERROR: invalid byte sequence for encoding "UTF8": 0xc92c
我如何解决这个问题? 我是否需要更改整个数据库的编码(如果是这样,怎么做?),还是只能更改我的tmp
表的编码? 或者我应该尝试更改文件的编码?
如果您需要将UTF8数据存储在数据库中,则需要一个接受UTF8的数据库。 你可以在pgAdmin中检查你的数据库的编码。 只需右键单击数据库,然后select“属性”。
但是这个错误似乎告诉你在源文件中有一些无效的UTF8数据。 这意味着copy
工具已经检测到或者猜测你正在给它一个UTF8文件。
如果你在Unix的某个版本下运行,你可以使用file
实用程序检查编码(或多或less)。
$ file yourfilename yourfilename: UTF-8 Unicode English text
(我认为这也可以在terminal上的Mac电脑上工作。)不知道如何在Windows下做到这一点。
如果您在来自Windows系统的文件(即, 未使用UTF8编码的文件)上使用相同的实用程序,则可能会显示如下所示:
$ file yourfilename yourfilename: ASCII text, with CRLF line terminators
如果事情保持怪异,你可能会尝试将你的input数据转换成已知的编码,或者改变客户端的编码。 (我们真的扩展了我对编码知识的限制。)
您可以使用iconv
实用程序更改input数据的编码。
iconv -f original_charset -t utf-8 originalfile > newfile
您可以按照字符集支持上的说明更改psql(客户端)编码。 在该页面上,search短语“启用自动字符集转换”。
psql=# copy tmp from '/path/to/file.csv' with delimiter ',' csv header encoding 'windows-1251';
添加encoding
选项在我的情况下工作。
显然,我可以在飞行中设置编码 ,
set client_encoding to 'latin1'
然后重新运行查询。 不知道我应该使用什么编码。
latin1
使得这些字符清晰可辨,但是大部分的重音字符都是大写字母,不应该是大写字母。 我认为这是由于一个不好的编码,但我认为它实际上是不好的数据。 我最终保持了latin1编码,但是预处理数据并修正了套pipe问题。
这个错误意味着文件中的logging编码与连接有所不同。 在这种情况下,iconv可能会返回错误,有时甚至是// IGNORE标志:
iconv -f ASCII -t utf-8 // IGNORE <b.txt> /a.txt
iconv:位置上的非法input序列(某些数字)
诀窍是find不正确的字符,并将其replace。 要在Linux上使用“vim”编辑器:
vim(你的文本文件),按“ESC”:button,然后input“:goto(iconv返回的数字)”
要查找非ASCII字符,您可以使用以下命令:
grep –color ='auto'-P“[\ x80- \ xFF]”
如果你删除不正确的字符,请检查你是否真的需要转换你的文件:可能问题已经解决了。
这取决于什么types的机器/编码生成您的导入文件。
如果你是从英文版或西欧版的Windows中获得的话,那么最好的办法就是把它设置为“WIN1252”。 如果您从其他来源获得该文件,请参阅此处的字符编码列表:
http://www.postgresql.org/docs/8.3/static/multibyte.html
如果你是从Mac获得的,你可能需要首先通过“iconv”工具来运行它,将它从MacRoman转换为UTF-8。
那么我面临着同样的问题。 什么解决了我的问题是这样的:
在Excel中点击另存为。 从保存types中select.csv点击工具 。 然后从下拉列表中selectWeb选项 。 在“ 编码”选项卡下,将文档另存为Unicode(UTF-8) 。 点击OK。 保存文件。 完成!
您可以使用sedreplace反斜杠字符,例如pipe道字符。
sed -i -- 's/\\/|/g' filename.txt
请按照以下步骤在pgadmin中解决此问题:
-
SET client_encoding = 'ISO_8859_5';
-
COPY tablename(column names) FROM 'D:/DB_BAK/csvfilename.csv' WITH DELIMITER ',' CSV ;
我有同样的问题,并find了一个很好的解决scheme: http : //blog.e-shell.org/134
这是由于你的数据库编码不匹配造成的,当然是因为你得到SQL转储的数据库被编码为SQL_ASCII,而新数据库编码为UTF8。 Recode是GNU项目中的一个小工具,可以让你快速更改给定文件的编码。
所以我只是在回放之前重新编码转储文件:
postgres> gunzip -c /var/backups/pgall_b1.zip | recode iso-8859-1..u8 | psql test
在Debian或Ubuntu系统中,recode可以通过包来安装。
如果丢弃不可转换字符可以,则可以使用-c
标志
iconv -c -t utf8 filename.csv > filename.utf8.csv
然后将它们复制到您的表格
如果input数据本身包含转义字符,则可能发生此错误。 默认情况下,转义字符是“\”符号,所以如果您的input文本包含“\”字符 – 请尝试使用ESCAPE选项更改默认值。
这个错误也很有可能是该字段被encryption的地方。 确保您正在查看正确的表格,在某些情况下,pipe理员将创build一个可以使用的未encryption视图。 我最近遇到了一个非常类似的问题。
当我试图将由Excel生成的csv复制到Postgres表(在Mac上)时,我得到了同样的错误。 这是我解决它的方法:
1)打开Atom中的File(我使用的IDE)
2)在文件中做一个微不足道的改变。 保存文件。 撤消更改。 再次保存。
普雷斯托! 复制命令现在工作。
(我认为Atom保存在一个工作的格式)
对于python,你需要使用
类pg8000.types.Bytea(str)Bytea是一个str派生类,映射到PostgreSQL字节数组。
要么
Pg8000.Binary(value)构造一个保存二进制数据的对象。
copy tablename from 'filepath\filename' DELIMITERS '=' ENCODING 'WIN1252';
你可以试试这个来处理UTF8编码。