使用 SQL 从 AS400 提取数据时出现问题
Problem with extracting data from AS400 using SQL
我正在编写一个 SQL 请求以使用不同的关系从 AS400 导出数据。
我想这样写,以减少时间并提高我的 ETL 的性能(我至少有 2900 万行在我的 ETL 中使用它)。
SQL:
SELECT A.x1, A.x2, A.x3, A.x4, A.x5,
(SELECT B.y1, B.y2, B.y3, C.w1 as w
FROM TEST1 AS B inner join TEST2 AS C ON ((C.w2=B.y4) and (C.w3=B.y5))
where (B.y6 = 2)),
E.q1
FROM TEST3 AS A
LEFT OUTER JOIN TEST1 AS B ON (A.x6 = B.y7)
LEFT OUTER JOIN TEST4 AS E ON ((A.x6 = E.q2) AND (A.x7 = E.q3))
这个错误我真的需要帮助
我遇到了这个异常:
TITRE : Microsoft Visual Studio
Exception de HRESULT : 0xC0202009
Erreur sur Traitement [Source [2]] : Code d'erreur SSIS DTS_E_OLEDBERROR. Une erreur OLE DB s'est produite. Code d'erreur : 0x80004005.
Un enregistrement OLE DB est disponible. Source : « IBMDA400 Command » Hresult : 0x80004005 Description : « SQL0412 : Sous-requête non admise, car plus d'une colonne résultat
Cause . . . . . : La sous-requête d'un prédicat doit avoir uniquement une colonne résultat correspondante lorsque l'autre opérande du prédicat est une expression simple. En effet, la sous-requête peut extraire zéro, une ou plusieurs valeurs constituant une liste mais apparaissant dans une seule colonne résultat. Que faire . . . : Modifiez le nombre d'éléments renvoyés par la sous-requête pour qu'il n'y ait qu'une seule colonne résultat ou remplacez l'autre opérande du prédicat pour obtenir une liste d'expressions. ».
您可以使用 "table expression" 代替 "scalar subquery" 加入额外数据。
标量子查询仅限于一行(您的可能 return 多行)和一列(您的显然试图 return 多于一列)。
例如,您可以这样做:
SELECT A.x1, A.x2, A.x3, A.x4, A.x5,
f.y1, f.y2, f.y3, f.w,
E.q1
FROM TEST3 AS A
LEFT OUTER JOIN TEST1 AS B ON (A.x6 = B.y7)
LEFT OUTER JOIN TEST4 AS E ON ((A.x6 = E.q2) AND (A.x7 = E.q3))
left join (
SELECT B.y1, B.y2, B.y3, C.w1 as w
FROM TEST1 AS B -- you should avoid reusing the same alias B, but OK
inner join TEST2 AS C ON ((C.w2=B.y4) and (C.w3=B.y5))
where (B.y6 = 2)
) f on 1 = 1 -- what's the join condition? I assume you want all rows to match
编辑以加快查询速度
您正在选择 table A
中的所有行;那肯定会很慢。尽管如此,由于您的联接是等值联接,因此它们可以从索引中受益匪浅;以下索引可以使您的查询更快:
create index ix1 on TEST1 (y7, x1, x2, x3, x4, x5);
create index ix2 on TEST1 (y6, y1, y2, y3);
create index ix3 on TEST4 (q2, q3, q1);
create index ix4 on TEST2 (w2, w3, w1);
您的错误原因是子查询返回了不止一列。 AlwaysLearning 已经说过了。
但下一个问题是您的子查询返回多行。
除非
SELECT B.y1, B.y2, B.y3, C.w1 as w
FROM TEST1 AS B inner join TEST2 AS C ON ((C.w2=B.y4) and (C.w3=B.y5))
where (B.y6 = 2)
只有 returns 一行。请注意,子查询没有与外部 select 相关的条件。在子查询中使用别名 B 不会将其与外部 select 相关联,因为它在 FROM TEST1 AS B
处的内部 select 中被重新定义。这使得别名成为子查询的本地别名,并在子查询的外部 select 中隐藏了 B 的使用。如果这不是您想要的,即使是,您也应该始终遵循 SQL 中的一条简单规则,不要重复使用别名。
我正在编写一个 SQL 请求以使用不同的关系从 AS400 导出数据。 我想这样写,以减少时间并提高我的 ETL 的性能(我至少有 2900 万行在我的 ETL 中使用它)。
SQL:
SELECT A.x1, A.x2, A.x3, A.x4, A.x5,
(SELECT B.y1, B.y2, B.y3, C.w1 as w
FROM TEST1 AS B inner join TEST2 AS C ON ((C.w2=B.y4) and (C.w3=B.y5))
where (B.y6 = 2)),
E.q1
FROM TEST3 AS A
LEFT OUTER JOIN TEST1 AS B ON (A.x6 = B.y7)
LEFT OUTER JOIN TEST4 AS E ON ((A.x6 = E.q2) AND (A.x7 = E.q3))
这个错误我真的需要帮助
我遇到了这个异常:
TITRE : Microsoft Visual Studio
Exception de HRESULT : 0xC0202009 Erreur sur Traitement [Source [2]] : Code d'erreur SSIS DTS_E_OLEDBERROR. Une erreur OLE DB s'est produite. Code d'erreur : 0x80004005. Un enregistrement OLE DB est disponible. Source : « IBMDA400 Command » Hresult : 0x80004005 Description : « SQL0412 : Sous-requête non admise, car plus d'une colonne résultat Cause . . . . . : La sous-requête d'un prédicat doit avoir uniquement une colonne résultat correspondante lorsque l'autre opérande du prédicat est une expression simple. En effet, la sous-requête peut extraire zéro, une ou plusieurs valeurs constituant une liste mais apparaissant dans une seule colonne résultat. Que faire . . . : Modifiez le nombre d'éléments renvoyés par la sous-requête pour qu'il n'y ait qu'une seule colonne résultat ou remplacez l'autre opérande du prédicat pour obtenir une liste d'expressions. ».
您可以使用 "table expression" 代替 "scalar subquery" 加入额外数据。
标量子查询仅限于一行(您的可能 return 多行)和一列(您的显然试图 return 多于一列)。
例如,您可以这样做:
SELECT A.x1, A.x2, A.x3, A.x4, A.x5,
f.y1, f.y2, f.y3, f.w,
E.q1
FROM TEST3 AS A
LEFT OUTER JOIN TEST1 AS B ON (A.x6 = B.y7)
LEFT OUTER JOIN TEST4 AS E ON ((A.x6 = E.q2) AND (A.x7 = E.q3))
left join (
SELECT B.y1, B.y2, B.y3, C.w1 as w
FROM TEST1 AS B -- you should avoid reusing the same alias B, but OK
inner join TEST2 AS C ON ((C.w2=B.y4) and (C.w3=B.y5))
where (B.y6 = 2)
) f on 1 = 1 -- what's the join condition? I assume you want all rows to match
编辑以加快查询速度
您正在选择 table A
中的所有行;那肯定会很慢。尽管如此,由于您的联接是等值联接,因此它们可以从索引中受益匪浅;以下索引可以使您的查询更快:
create index ix1 on TEST1 (y7, x1, x2, x3, x4, x5);
create index ix2 on TEST1 (y6, y1, y2, y3);
create index ix3 on TEST4 (q2, q3, q1);
create index ix4 on TEST2 (w2, w3, w1);
您的错误原因是子查询返回了不止一列。 AlwaysLearning 已经说过了。
但下一个问题是您的子查询返回多行。
除非
SELECT B.y1, B.y2, B.y3, C.w1 as w
FROM TEST1 AS B inner join TEST2 AS C ON ((C.w2=B.y4) and (C.w3=B.y5))
where (B.y6 = 2)
只有 returns 一行。请注意,子查询没有与外部 select 相关的条件。在子查询中使用别名 B 不会将其与外部 select 相关联,因为它在 FROM TEST1 AS B
处的内部 select 中被重新定义。这使得别名成为子查询的本地别名,并在子查询的外部 select 中隐藏了 B 的使用。如果这不是您想要的,即使是,您也应该始终遵循 SQL 中的一条简单规则,不要重复使用别名。