我有一个小表和某个字段包含类型“字符变化”。我试图将其更改为“整数”,但它给出了一个错误,casting是不可能的。

是否有办法解决这个问题,或者我应该创建另一个表,并使用查询将记录带入其中。

该字段只包含整数值。


当前回答

你可以这样做:

change_column :table_name, :column_name, 'integer USING CAST(column_name AS integer)'

或者试试这个:

change_column :table_name, :column_name, :integer, using: 'column_name::integer'

如果您对这个主题感兴趣,请阅读这篇文章:https://kolosek.com/rails-change-database-column

其他回答

我也有同样的问题。我开始重置列的默认值。

change_column :users, :column_name, :boolean, default: nil
change_column :users, :column_name, :integer, using: 'column_name::integer', default: 0, null: false

如果你不小心把整数和文本数据混合了,你应该首先执行下面的update命令(如果不是上面的alter表将失败):

UPDATE the_table SET col_name = replace(col_name, 'some_string', '');

字符变化中的空字符串或空值

如果你有一个包含空字符串或null的列,你可能会遇到错误消息:

整数类型的输入语法无效:""

解决方案

使用coalesce和nullif来获取空字符串,使用nulls来获取零值。

ALTER TABLE peopleGroup ALTER numberPeople TYPE INT USING (cast ( coalesce( nullif( trim(numberPeople), '' ), '0' ) as integer ))

我也有同样的问题。 然后我意识到我有一个默认字符串值的列,我试图改变。 删除默认值使错误消失:)

没有从文本或varchar到整数的隐式(自动)转换(也就是说,你不能将varchar传递给一个期望整数的函数,也不能将varchar字段分配给整数),所以你必须使用ALTER TABLE指定一个显式的转换…修改列…类型……使用:

ALTER TABLE the_table ALTER COLUMN col_name TYPE integer USING (col_name::integer);

请注意,您的文本字段中可能有空白;在这种情况下,使用:

ALTER TABLE the_table ALTER COLUMN col_name TYPE integer USING (trim(col_name)::integer);

在转换前去掉空白。

如果命令在psql中运行,这应该从错误消息中很明显,但可能PgAdmin-III没有显示完整的错误。下面是如果我在PostgreSQL 9.2上用psql测试它会发生什么:

=> CREATE TABLE test( x varchar );
CREATE TABLE
=> insert into test(x) values ('14'), (' 42  ');
INSERT 0 2
=> ALTER TABLE test ALTER COLUMN x TYPE integer;
ERROR:  column "x" cannot be cast automatically to type integer
HINT:  Specify a USING expression to perform the conversion. 
=> ALTER TABLE test ALTER COLUMN x TYPE integer USING (trim(x)::integer);
ALTER TABLE        

感谢@muistooshort添加USING链接。

参见这个相关的问题;它是关于Rails迁移的,但是潜在的原因是相同的,答案是适用的。

如果错误仍然发生,那么它可能与列值无关,而是与此列的索引或列默认值有关,可能无法进行类型转换。索引需要在ALTER COLUMN之前删除,在ALTER COLUMN之后重新创建。应适当更改默认值。