【问题标题】:<table-valued function> is not a recognized built-in function name<table-valued function> 不是可识别的内置函数名称
【发布时间】:2012-03-05 23:19:45
【问题描述】:

我收到此错误:

消息 195,第 15 级,状态 10,第 1 行
'fnParseName' 不是可识别的内置函数名称。

关于这个查询:

SELECT  fnParseName(DOCTORFIRSTNAME+' ' +DOCTORLASTNAME) 
  FROM [PracticeandPhysician]

这是 fnParseName 的代码

create FUNCTION [dbo].[fnParseName]
               (@FullName NVARCHAR(128))
RETURNS @FullNameParts TABLE  (FirstName  NVARCHAR(128),
                               Middle     NVARCHAR(128),
                               LastName   NVARCHAR(128))
AS
  BEGIN
    ... function body that populates @FullNameParts ...
    RETURN
  END

为什么会出现这个错误?

【问题讨论】:

  • 这是一个表值函数,如果有帮助的话

标签: sql sql-server sql-server-2008


【解决方案1】:

这是一个表值函数。所以你可能的意思是:

SELECT p.DOCTORFISTNAME, p.DOCTORLASTNAME, t.FirstName, t.Middle, t.LastName
  FROM dbo.[PracticeandPhysician] AS p
  CROSS APPLY dbo.fnParseName(p.DOCTORFIRSTNAME + ' ' + p.DOCTORLASTNAME);

请注意,您不能说:

SELECT dbo.TableValueFunction('foo');

你可以说的更多:

SELECT dbo.Table;
--or
SELECT dbo.View;

不过,你可以说:

SELECT * FROM dbo.fnParseName('foo bar');
--or
SELECT FirstName, Middle, LastName FROM dbo.fnParseName('foo bar');

(并不是说我已经验证了您的函数是否按照您的想法执行,或者执行效率很高。)

请按照其他人的建议always use the dbo. prefix。

【讨论】:

  • 我不是在第一个示例中使用CROSS APPLY 展示了这一点吗?它应该从dbo.[PracticeandPhysician] 中的每个输入行输出列。
  • "CROSS APPLY 仅返回外部表中的行,这些行从表值函数产生结果集。"来自 MSDN 文档:msdn.microsoft.com/en-us/library/ms175156.aspx
  • 加一表示“始终使用 dbo 前缀”
【解决方案2】:

您始终必须在 SQL 函数调用前加上架构名称 dbo. 或该函数的架构名称(dbo 是默认架构)。

SELECT dbo.fnParseName(--etc

【讨论】:

  • Msg 4121,级别 16,状态 1,行 2 找不到列“dbo”或用户定义的函数或聚合“dbo.fnParseName”,或者名称不明确。
  • @MattGibson 不,绝对不是,如果你愿意,我可以给你发快照
  • @MattGibson 如果有帮助,它是一个表值函数
  • 是的,请检查您是否不小心在 master 上创建了该函数。打开新连接以运行 sql 批处理时,它很容易完成。
  • @Peter 这是一个表值函数。前缀很重要,但真正的问题是您不能像表达式一样引用表值函数(尽管您可以使用标量 UDF)。
【解决方案3】:

UDF/函数需要以模式名称为前缀(最有可能是“dbo”)。将调用改为

SELECT
    dbo.fnParseName(DOCTORFIRSTNAME + ' ' + DOCTORLASTNAME) 
FROM
    [PracticeandPhysician]

【讨论】:

  • Msg 4121,级别 16,状态 1,行 2 找不到列“dbo”或用户定义的函数或聚合“dbo.fnParseName”,或者名称不明确。
  • 架构前缀不是这里的问题(虽然它仍然是必需的,但存在更基本的语法问题)。
【解决方案4】:

您遇到的问题和我遇到的类似。标量函数和表内联函数在实现方面有很大不同。不同之处见下文

 Create function udfCountry
 (
@CountryName varchar(50)
 )
 returns varchar(2)
 as 
 BEGIN
 Declare @CountryID varchar(2),
    @Result varchar(2)

 Select @CountryID = Country from 
dbo.GeoIPCountryNames where CountryName = @CountryName

set @Result = isNull(@CountryID, 'NA')
if @Result = 'NA'
set @Result = 'SD'
return @Result
End

//实现

select dbo.[udfCountry]('Nigeria')

//样本结果

NG

// 内联表函数示例

 Create FUNCTION  ConditionEvaluation
 (
  @CountrySearch varchar(50)
 )
 returns @CountryTable table 
(
Country varchar(2),
CountryName varchar(50)
 )
 as 

 Begin

 Insert into @CountryTable(Country, CountryName)
 Select Country, CountryName from GeoIPCountryNames
 where Country like '%'+@CountrySearch+'%'
 return 
 end

//实现示例

 Declare @CountrySearch varchar(50)
 set @CountrySearch='a'
 select * from  ConditionEvaluation(@CountrySearch)

实现标量的部分是完全不同的内联表。我希望这会有所帮助

【讨论】:

    【解决方案5】:

    如果要将tfn返回的值赋值给存储过程的一个变量,可以这样:

    select  @my_local_variable_in_procedure = column_name_returned_from_tfn from dbo.my_inline_tfn (@tfn_parameter)
    

    【讨论】:

      猜你喜欢
      • 2014-06-12
      • 2014-01-25
      • 2017-04-16
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-02-08
      • 1970-01-01
      相关资源
      最近更新 更多