2015-05-20 9 views
8

Ich habe eine Zeichenfolge wie untenSplit ein Teil, die von einer Split-Funktion gibt

a_b|c_d 

und ich brauche es zu teilen, basierend auf |.

So wird das Ergebnis sein:

a_b 
c_d 

Dann will ich es mit _ wieder spalten, dann führt sein:

a 
b 

c 
d 

Ist es möglich, dies in einem einzigen zu tun Schritt? Wie, wenn die Eingabe der entsprechenden Zeichenfolge, wird es einen Wert zurückgeben wie folgt vor:

a 
b 
c 
d 

Ich habe eine Funktion für Split erstellt:

select items from dbo.splitdetails('a_b|c_d','|') 

Es wird zur Folge haben:

a_b 
c_d 

Aber ich weiß nicht, wie kann ich mit diesen Ergebnissen den nächsten Split machen?

Mit temporäre Tabelle, ich hoffe, ich kann dies tun, aber ich muss dies innerhalb einer Funktion verwenden. Also ich denke temporäre Tabelle ist keine gute Option. Cursor ist auch eine Option, aber wenn ich Cursor verwende, wird es die Leistung verschlechtern, weil ich Tausende von Datensätzen habe.

Meine Eingabe ist:

a_b|c_d 

und legte gewünschte out ist:

a 
b 
c 
d 
+2

Haben Sie darüber nachgedacht, einen Datentyp zu verwenden, der * entworfen * wurde, um mehrere Werte wie XML oder Tabellen zu speichern, anstatt dieses Problem für sich selbst zu erstellen? –

Antwort

7

Sie können besser Sql Replace Funktion zuerst verwenden und dann als Split-Funktion verwenden, unter

select REPLACE('a_b|c_d','|','_') 

results: a_b_c_d 

nun wie Ihre Split-Funktion verwenden, unter

select items from dbo.splitdetails('a_b_c_d','_') 

EDIT:

zu einer Zeit All

select items from dbo.splitdetails(REPLACE('a_b|c_d','|','_'),'_') 

EDIT1:

In diesem Fall Verwenden Sie die Option Ersetzen in umge

select items from dbo.splitdetails(REPLACE('a_b|c_d','_','|'),'|') 
+0

yup verschlechtert hat einen Versuch .. Dank für Ihre gültige suggection –

+0

Dank Ihrer Lösung funktioniert, aber unfortunalty ich diese Lösung nicht verwenden kann, weil _ und | kann in meiner Logik verschiedene Bedeutungen haben. also wenn ich | mit _ dann ganze Logik wird –

+0

fehlschlägt sowieso Ihre Antwort gibt Antwort auf meine Frage .so muss es akzeptiert werden. –

2

in SQL ein CURSOR

ist dann fetch verwenden, um jede SubString vom 1. zu erhalten wählen

DECLARE db_cursor CURSOR FOR 
select items 
from bdo.splitdetails('a_b|c_d','|') 

OPEN db_cursor 
FETCH NEXT FROM db_cursor INTO @items 

WHILE @@FETCH_STATUS = 0 
BEGIN 
    select SubString 
    from bdo.splitdetails(@items,'_') 

    --do something on SubString-- 

    FETCH NEXT FROM db_cursor INTO @items 
END 

CLOSE db_cursor 
DEALLOCATE db_cursor 
+0

Wenn ich Cursor verwende, wird es die Leistung verschlechtern, ich muss eine lange Zeichenfolge basierend auf vielen Bedingungen aufteilen und ich muss es mit einer Join-Abfrage tun, so kann es Tausende von Datensätzen haben. so, wenn ich Cursor dann für jeden Datensatz i-Schleife muß so wird es performnce –

1

Ist diese Hilfe ..

With value(Item) as 
(
select items from bdo.splitdetails('a_b|c_d','|') 
) 
Select x.Items from value a 
cross apply ( 
select items from bdo.splitdetails(a.Item,'_') 
) x ; 
5

Sie können CROSS APPLY wie folgt verwenden.

SELECT d.item,e.item from dbo.splitdetails('a_b|c_d','|') d 
CROSS APPLY dbo.splitdetails(d.item,'_') e 
+0

Dank @ImranAliKhan um Hilfe Quer gelten eine gute Option ist .. –

+0

leider zeigt es ein Fehler Msg 102, Ebene 15, Status 1, Zeile 2 Falsche Syntax in der Nähe '.'. –

+0

ah, es ist, weil ich den Schemanamen von Ihrer ursprünglichen Frage – ughai

0

Eingesetzt werden können diese

select items from bdo.splitdetails(REPLACE('a_b|c_d','|','_'),'_') 
1

helfen Sie sich PATINDEX Funktion können Sie die Zeichenfolge, die durch mehrere Trennzeichen spalten. Hier ist die komplette Funktion und Beispielausgabe.

CREATE FUNCTION [dbo].[splitdetails] 
(
    @input VARCHAR(100), 
    @delim VARCHAR(100) 
) 
RETURNS @table TABLE 
(
    items VARCHAR(100) 
) 
AS 
BEGIN 
    DECLARE @index INT; 
    SET @index = PATINDEX(@delim, @input) 
    WHILE @index > 0 
    BEGIN 
     INSERT INTO @table SELECT LEFT(@input, @index - 1) 
     SET @input = RIGHT(@input, LEN(@input) - @index) 
     SET @index = PATINDEX(@delim, @input) 
    END 
    INSERT INTO @table SELECT @input 
    RETURN 
END 
GO 

SELECT items FROM dbo.splitdetails('a_b|c_d', '%[_|]%') 
-- a 
-- b 
-- c 
-- d 

SELECT items FROM dbo.splitdetails('xxx|yyy', '%[_|]%') 
-- xxx 
-- yyy 

SELECT items FROM dbo.splitdetails('xxxxxxx', '%[_|]%') 
-- xxxxxxx 
+0

Danke nette Lösung. –