我目前正在开展一项将日期从PostgreSQL迁移到另一个PostgreSQL数据库的任务。一个字段的数据需要分成三列(例如,father_name,需要拆分为f_name,f_middle_name,f_last_name)我通过网络搜索,我想我可以使用string_to_array来完成这项任务。现在我的问题是如何将字符串的数组索引分配给目标DB的字段(目标DB具有f_name,f_middle_name,f_last_name,而源DB只有father_name字段)。
cur_t.execute("""
SELECT TRANSLATE(studentnumber, '- ', ''), string_to_array(father_name)
cur_p.execute(""" INSERT INTO "a_recipient" (student_id, f_name, f_middle_name, f_last_name) VALUES ('%s', '%s', '%s', '%s') """ % (row[0]
row[1][0], row[1][1], row[1][2]))
我只是不知道如何访问数组的索引并将其作为值分配给目标字段。
参考文献:string_to_array string_to_array
有什么建议吗?
答案 0 :(得分:1)
虽然it is possible to turn an array into a set of columns你没有固定的一组列。例如,如果您将father_name
拆分为三个适用于John Wilkes Booth
的部分,但Yarrow Hock
呢?还是Beyoncé
?还是Bernal Diaz Del Castillo
?你需要更聪明的东西,而不仅仅是分裂空白。
虽然可能在Postgresql中编写内容,可能是stored procedure,但在Python中进行数据转换比较容易,但速度较慢。因为你必须通过Python运行数据(或者做一些复杂的事情来链接两个数据库),并且因为这是(希望)一次性的事情,所以性能并不重要。
我不擅长Python,但它会是这样的。
cur_t.execute("""SELECT studentnumber, father_name FROM something""")
for row in cur_t:
father = parse_name(row['father_name'])
student_id = fix_studentnumber(row['studentnumber'])
cur_p.execute("""
INSERT INTO "a_recipient" (student_id, f_name, f_middle_name, f_last_name)
VALUES ('%s', '%s', '%s', '%s')
""" % (student_id, father['first'], father['middle'], father['last'])
)
然后你会编写parse_name
和fix_studentnumber
以及任何其他必要的函数来清理Python中的数据。你可以对它们进行单元测试。
注意:因为按编号访问列(即。row[5]
)很难阅读和维护,所以您可能希望使用conn_t.cursor(cursor_factory=psycopg2.extras.DictCursor)
,因此您可以按照上面的名称访问列。< / p>
答案 1 :(得分:0)
为什么不直接在SQL上执行:
vao@so=# create table so12(a text, b text, c text);
CREATE TABLE
vao@so=# with a(i) as (values('1,2,5'))
, s as (select string_to_array(i,',') ar from a)
insert into so12 select ar[1],ar[2],ar[3] from s;
INSERT 0 1
vao@so=# select * from so12;
┌───┬───┬───┐
│ a │ b │ c │
├───┼───┼───┤
│ 1 │ 2 │ 5 │
└───┴───┴───┘
(1 row)
<强>更新强>
我错过了它发生在几个数据库的范围内的点,因此您需要使用dblink
或创建一个postgres_fdw
外表。两者仍然比选择数组然后使用insert into .. values(..)
语句