函数无法识别_PostgreSQL找不到最佳函数问题解析
最近給項(xiàng)目做支持,由于函數(shù)類型問題,加了幾條函數(shù)定義。
用戶使用函數(shù)場景是func('string', 'string')。當(dāng)時(shí)給用戶添加了一條函數(shù)定義:func(text, text)。后來由于和其他函數(shù)沖突改成了func(varchar, varchar)。varchar和text同樣都是字符串類型,而且用的相同的結(jié)構(gòu)體,我的感知是效果是相同的,然后在使用過程中還是發(fā)生錯(cuò)誤:
ERROR: function func(unknown, unknown) is not unique LINE 1: select func('****','****');^ HINT: Could not choose a best candidate function. You might need to add explicit type casts.這里的問題是,使用varchar,unknown不會默認(rèn)轉(zhuǎn)為varchar。而當(dāng)參數(shù)類型是text時(shí),就會默認(rèn)轉(zhuǎn)為text,然后在進(jìn)行查找,這很奇怪了。開始定位原因,發(fā)現(xiàn)在執(zhí)行函數(shù)func_select_candidate,會有不同。func_select_candidate代碼非常長,這里就不貼出來了,大家可以自行看下,我在這里簡單對代碼進(jìn)行介紹:
/* * 函數(shù)正式由于存在unknown type,所以無法準(zhǔn)確定位到目標(biāo)函數(shù),* 所以這個(gè)函數(shù)主要用來處理帶有unknown type的函數(shù)查詢*/ func_select_candidate() { /* Step 1 */ 處理有一個(gè)或多個(gè)unknown type的函數(shù),盡可能匹配到相同類型的函數(shù), 如果候選者只有一個(gè)則返回,否則進(jìn)入下一步; 如果沒有候選者,則返回NULL; /* Step 2 */ 如果還是有多個(gè)候選函數(shù),那么通過查找最優(yōu)先類型函數(shù)(typispreferred為true的類型), 如果候選者只有一個(gè)則返回,否則進(jìn)入下一步; 如果沒有候選者,則返回NULL; /* Step 3 */ 如果還是有多個(gè)候選函數(shù),那么嘗試將unknown type嘗試轉(zhuǎn)換為最優(yōu)先類型函數(shù); 如果候選者只有一個(gè)則返回,否則進(jìn)入下一步; 如果沒有候選者,則返回NULL; /* Step 4 */ 如果上一步確認(rèn)可以轉(zhuǎn)到最優(yōu)先類型,則嘗試進(jìn)行使用最優(yōu)先類型進(jìn)行匹配函數(shù); 如果候選者只有一個(gè)則返回,否則進(jìn)入下一步; 如果沒有候選者,則返回NULL; /* Step 5 */ 如果還是沒有找到最有函數(shù),并且unknown type參數(shù)個(gè)數(shù)少于總的參數(shù)個(gè)數(shù), 則嘗試將所有的unknown type轉(zhuǎn)換為已知的類型接收,并且查看是否可以將已知類型轉(zhuǎn)換為函數(shù)類型, 一旦找到即返回,否則返回NULL; }這里的typispreferred和typcategory引起了我的注意,可以查看文檔:
typcategory:typcategoryis an arbitrary classification of data types that is used by the parser to determine which implicit casts should be“preferred”. SeeTable 51.64.typispreferred:True if the type is a preferred cast target within itstypcategory
查看系統(tǒng)表:
postgres=# select oid,typname,typcategory,typispreferred from pg_type where oid=1043 or oid = 25 or oid = 705; oid | typname | typcategory | typispreferred ------+---------+-------------+----------------25 | text | S | t705 | unknown | X | f1043 | varchar | S | f (3 rows)text是typcategory為‘S’的preferred類型。
我定義的func(text, text),進(jìn)入了func_select_candidate的part3和4,完成了匹配,而如果是func(varchar, varchar)由于不滿足part3、4、5,直接返回NULL,返回?zé)o法找到最優(yōu)函數(shù)的錯(cuò)誤。這也就是類型使用text能夠完成函數(shù)識別而varchar不能的原因。
總結(jié)
以上是生活随笔為你收集整理的函数无法识别_PostgreSQL找不到最佳函数问题解析的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 成都大熊猫繁育基地最近的地铁站
- 下一篇: 作为唯一索引_Mysql什么情况下不走索