2013-08-06 59 views
40

在我的SELECT語句中,我得到了以下錯誤之一:未能找到未知的轉換功能,文本

ERROR: failed to find conversion function from unknown to text 
********** Error ********** 
ERROR: failed to find conversion function from unknown to text 
SQL state: XX000 

這是很容易使用cast來解決,但我不完全理解爲什麼會發生。我會用兩個簡單的陳述來解釋我的困惑。

這一個是OK:

select 'text' 
union all 
select 'text'; 

這將返回錯誤:

with t as (select 'text')  
select * from t 
union all 
select 'text' 

我知道我可以很容易地解決這個問題:

with t as (select 'text'::text)  
select * from t 
union all 
select 'text' 

爲什麼轉換失敗的第二個例子?有沒有一些我不明白的邏輯,或者這將在未來的Pos​​tgreSQL版本中被修復?

的PostgreSQL 9.1.9

上的PostgreSQL 9.2.4(SQL Fiddle)相同的行爲

回答

36

Postgres的是快樂的,如果它可以檢測類型從上下文無類型常量。但是,如果任何上下文不可行,並且查詢稍微複雜一點,那麼此機制就會失敗。這些規則對於任何SELECT子句都是特定的,有些更嚴格,有些則沒有。如果我可以說,那麼舊的例程更寬容(由於與甲骨文的兼容性較高,對初學者的負面影響較小),現代人較不寬容(因爲類型錯誤的安全性較高)。

有一些建議嘗試處理任何未知文字常量,如文本常量,但由於更多原因被拒絕。所以我不希望這方面發生重大變化。這個問題通常與綜合測試相關 - 而不是真正的查詢,其中類型是從列類型中推導出來的。

+2

我明白了。我在現實生活中經常遇到這個問題。我們使用PostgreSQL進行分析/雙向/數據挖掘,並且非類型常量的並集很常見。但正如我所說,這很容易施展。 –

+1

爲什麼我不需要像'1 :: int'那樣輸入數字文字? –

+0

@IainElder - 數字類型是較小的類 - 任何字面常量(命名爲「未知」)可隱式轉換爲任何類型 - 數字不是 - 因此sin('2.34')正在工作,但長度(1)不是 –