Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/sql/79.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/sql-server-2005/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Sql 从项目字符串中选择项目_Sql_Sql Server 2005_Tsql - Fatal编程技术网

Sql 从项目字符串中选择项目

Sql 从项目字符串中选择项目,sql,sql-server-2005,tsql,Sql,Sql Server 2005,Tsql,我有一组电子邮件收件人,格式如下: DECLARE @recipients VARCHAR(MAX); .... PRINT @recipients; /* the result person1@yahoo.com;person2@hotmail.com;person1@yahoo.com;... */ 选择DISTIECT。。。是一个简单而强大的SQL语句,但它可以针对表工作。有没有一种简单的方法可以从收件人列表变量中选择不同的收件人,比如C或Ruby中的FOR loop FO

我有一组电子邮件收件人,格式如下:

 DECLARE @recipients VARCHAR(MAX);
 ....
 PRINT @recipients;
 /* the result
 person1@yahoo.com;person2@hotmail.com;person1@yahoo.com;...
 */
选择DISTIECT。。。是一个简单而强大的SQL语句,但它可以针对表工作。有没有一种简单的方法可以从收件人列表变量中选择不同的收件人,比如C或Ruby中的FOR loop

 FOR @recipient IN @recipients
 BEGIN
    -- send email to @recipient
 END

顺便说一句,我正在SQL server 2005中使用TSQL。

在一个将返回一个表供您使用的拆分函数中,您需要什么


有无数种实现,但我不知道是否有内置的实现,也不知道是否有“最佳”的共识。

在将返回一个表供您使用的拆分函数中,您想要什么


有无数的实现,但我不知道有内置的实现,也不知道有“最佳”的共识。

这里有一个使用临时表的解决方案

declare @emails varchar(2000)
set @emails = 'person1@yahoo.com;person2@hotmail.com;person1@yahoo.com;'

declare @results table (row int identity(1,1), email varchar(500))

while ((select charindex(';',@emails)) > 0)
begin   
    insert into @results select substring(@emails,1,charindex(';',@emails))
    select @emails = substring(@emails,charindex(';',@emails)+1,len(@emails))
end

select distinct email from @results
其思想是从字符串中连续解析电子邮件,将其插入到临时表中,然后从剩余字符串中删除解析后的电子邮件


之后,您可以使用临时表循环发送个人电子邮件。

这里有一个使用临时表的解决方案

declare @emails varchar(2000)
set @emails = 'person1@yahoo.com;person2@hotmail.com;person1@yahoo.com;'

declare @results table (row int identity(1,1), email varchar(500))

while ((select charindex(';',@emails)) > 0)
begin   
    insert into @results select substring(@emails,1,charindex(';',@emails))
    select @emails = substring(@emails,charindex(';',@emails)+1,len(@emails))
end

select distinct email from @results
其思想是从字符串中连续解析电子邮件,将其插入到临时表中,然后从剩余字符串中删除解析后的电子邮件

之后,您可以使用临时表循环发送您的个人电子邮件。

例如

CREATE FUNCTION dbo.Split (@sep char(1), @s varchar(512))
RETURNS table
AS
RETURN (
    WITH Pieces(pn, start, stop) AS (
      SELECT 1, 1, CHARINDEX(@sep, @s)
      UNION ALL
      SELECT pn + 1, stop + 1, CHARINDEX(@sep, @s, stop + 1)
      FROM Pieces
      WHERE stop > 0
    )
    SELECT pn,
      SUBSTRING(@s, start, CASE WHEN stop > 0 THEN stop-start ELSE 512 END) AS s
    FROM Pieces
  )
GO
e、 g


当从前端接收类似列表时,我使用下面的函数来处理类似的情况。然后,您可以使用以下代码将字符串作为表返回:

SELECT DISTINCT String FROM dbo.GetTableFromStringList(@recipients)
不过,您可能希望使用T-SQL代码以外的其他代码来实际发送电子邮件

下面是函数:

CREATE FUNCTION [dbo].[GetTableFromStringList]
(
    @StringList VARCHAR(1000),
    @Delimiter  CHAR(1) = ','
)
RETURNS @Results TABLE
(
    String  VARCHAR(1000)   NOT NULL
)
AS
BEGIN
    DECLARE
        @string     VARCHAR(1000),
        @position   SMALLINT

    SET @StringList = LTRIM(RTRIM(@StringList)) + @Delimiter
    SET @position = CHARINDEX(@Delimiter, @StringList)

    WHILE (@position > 0)
    BEGIN
        SET @string = LTRIM(RTRIM(LEFT(@StringList, @position - 1)))

        IF (@string <> '')
        BEGIN
            INSERT INTO @Results (String) VALUES (@string)
        END

        SET @StringList = RIGHT(@StringList, LEN(@StringList) - @position)
        SET @position = CHARINDEX(@Delimiter, @StringList, 1)
    END

    RETURN
END

当从前端接收类似列表时,我使用下面的函数来处理类似的情况。然后,您可以使用以下代码将字符串作为表返回:

SELECT DISTINCT String FROM dbo.GetTableFromStringList(@recipients)
不过,您可能希望使用T-SQL代码以外的其他代码来实际发送电子邮件

下面是函数:

CREATE FUNCTION [dbo].[GetTableFromStringList]
(
    @StringList VARCHAR(1000),
    @Delimiter  CHAR(1) = ','
)
RETURNS @Results TABLE
(
    String  VARCHAR(1000)   NOT NULL
)
AS
BEGIN
    DECLARE
        @string     VARCHAR(1000),
        @position   SMALLINT

    SET @StringList = LTRIM(RTRIM(@StringList)) + @Delimiter
    SET @position = CHARINDEX(@Delimiter, @StringList)

    WHILE (@position > 0)
    BEGIN
        SET @string = LTRIM(RTRIM(LEFT(@StringList, @position - 1)))

        IF (@string <> '')
        BEGIN
            INSERT INTO @Results (String) VALUES (@string)
        END

        SET @StringList = RIGHT(@StringList, LEN(@StringList) - @position)
        SET @position = CHARINDEX(@Delimiter, @StringList, 1)
    END

    RETURN
END

您的建议似乎不是简单的TSQL方法。该函数接受两个参数,一个是收件人,另一个是分隔符,如“;”默认情况下。是吗?当然。您可以将任意分隔符设置为默认值。就简单T-SQL方式而言,函数是T-SQL的内置部分,我相信自SQL Server 2005以来,表值函数就一直存在。@David Chu:SQL Server中没有“简单”方式。在SQL支持数组之前,您必须通过手动方式来实现这一点-通过解析分隔字符串。您的建议看起来这不是一种简单的TSQL方式。该函数接受两个参数,一个是收件人,另一个是分隔符,如“;”默认情况下。是吗?当然。您可以将任意分隔符设置为默认值。就简单T-SQL方式而言,函数是T-SQL的内置部分,我相信自SQL Server 2005以来,表值函数就一直存在。@David Chu:SQL Server中没有“简单”方式。在SQL支持数组之前,您必须通过手动方式来实现这一点——解析一个分隔字符串。我得到了一个错误:递归查询片段SOK的“开始”列中的锚和递归部分之间的类型不匹配。我把错误解决了。我用了@s varcharmax。不知道max为什么不在这里工作。512或4000是OKI GET错误:递归查询片段SOK的列开始中的锚和递归部分之间的类型不匹配。我把错误解决了。我用了@s varcharmax。不知道max为什么不在这里工作。512或4000就可以了