2010-11-26 114 views
1

例如,我有串'This Is An Example Of The String'
,我想回到这个结果'This is an Example of the String'
==>我希望所有的“”,“”“”和'''在其他情况下,其余的应该留在Initcap中。SQL - 处理字符串

如何才能做到这一点在一个简单而独特的查询?这里是我的查询,以较低的情况下,只有“”:

SELECT 'This Is An Example Of The String', 
     CASE 
     WHEN 'This Is An Example Of The String' like '% Of %' 
     THEN replace('This Is An Example Of The String', ' Of ', ' of ') 
     END 
    FROM dual ; 

谢谢!

+0

这可能可以使用regexp_replace()完成,但我从来没有用过正则表达式组(在这种情况下需要这样做) – 2010-11-26 14:36:09

回答

4

试试这个:

SELECT REPLACE(REPLACE(REPLACE(REPLACE('This Is An Example Of The String', 'Of', 'of'), 'The', 'the'), 'An', 'an'), 'Is', 'is') FROM dual; 

我觉得有点脏写,虽然之后。

编辑:删除多余的'an'替换,然后添加缩进,然后再次删除缩进。无论你如何包装它,它看起来都很丑。

+1

我觉得它有点脏,但你是对的! :) – Timbo 2010-11-26 14:33:04

+0

有时几乎没有必要的罪恶=)并不意味着我必须喜欢它们。 – JonVD 2010-11-26 14:35:00

2

基本上它会采取很多你描述的性质的逻辑。没有快捷简单的方法。在业务逻辑代码中而不是在数据库中执行这种类型的操作会更快更容易。

如果您打算在数据库中执行此操作,请考虑在功能中封装逻辑,如this one

0

我可以告诉你的算法,但我不知道如何在SQL中做到这一点。例如:

words[] = string.split(" ") 
foreach word in words 
---if(word.length<=3) //do that only for short words 
-------if(word[i]>=65 && word[i]<=90) //check the ascii code for upper case 
------------word[i] += 21; // transfer it into lower case 
---new sentence += " " + words[i] //add to the resultant string 
2

虽然它不是一个纯粹的SQL解决方案,另一种选择是将其定义为需要,该转化的字符串的函数,也许叫它REPLACE_MULTI。调用会是这样的

SELECT REPLACE_MULTI('This Is An Example Of The String', 
        'Is|An|Of|The', 
        'is|an|of|the') 
    FROM DUAL; 

和实施将沿

CREATE OR REPLACE FUNCTION REPLACE_MULTI(strOriginal   IN VARCHAR2, 
             strTokens_to_replace IN VARCHAR2, 
             strReplacement_tokens IN VARCHAR2) 
    RETURN VARCHAR2 
IS 
    strResult    VARCHAR2(2000); 
    arrTokens_to_replace DBMS_SQL.VARCHAR2A; 
    arrReplacement_tokens DBMS_SQL.VARCHAR2A; 
    i      NUMBER; 

    FUNCTION extract_tokens(p_string IN VARCHAR2, 
          p_separators IN VARCHAR2) RETURN DBMS_SQL.VARCHAR2A 
    IS 
    arrTokens DBMS_SQL.VARCHAR2A; 
    BEGIN 
    WITH sel_string AS 
     (SELECT p_string AS fullstring FROM DUAL) 
    SELECT SUBSTR(fullstring, beg + 1, end_p - beg - 1) AS token 
     BULK COLLECT INTO arrTokens 
     FROM (SELECT beg, LEAD(beg) OVER (ORDER BY beg) AS end_p, fullstring 
       FROM (SELECT beg, fullstring 
         FROM (SELECT LEVEL beg, fullstring 
           FROM sel_string 
           CONNECT BY LEVEL <= LENGTH(fullstring)) 
         WHERE INSTR(p_separators, SUBSTR(fullstring, beg, 1)) > 0 
        UNION ALL 
         SELECT 0, fullstring FROM sel_string 
        UNION ALL 
         SELECT LENGTH(fullstring) + 1, fullstring FROM sel_string)) 
     WHERE end_p IS NOT NULL AND 
      end_p > beg + 1; 

    RETURN arrTokens; 
    END extract_tokens; 

BEGIN 
    arrTokens_to_replace := extract_tokens(strTokens_to_replace, '|'); 
    arrReplacement_tokens := extract_tokens(strReplacement_tokens, '|'); 

    strResult := strOriginal; 

    FOR i IN 1..arrTokens_to_replace.COUNT LOOP 
    strResult := REGEXP_REPLACE(strResult, 
           '^' || arrTokens_to_replace(i) || ' ', 
           arrReplacement_tokens(i)); 
    strResult := REPLACE(strResult, 
         ' ' || arrTokens_to_replace(i) || ' ', 
         ' ' || arrTokens_to_replace(i) || ' '); 
    strResult := REGEXP_REPLACE(strResult, 
           ' ' || arrTokens_to_replace(i) || '$', 
           ' ' || arrReplacement_tokens(i)); 
    END LOOP; 

    RETURN strResult; 
END REPLACE_MULTI; 

我敢肯定,有哪些可以创建令牌字符串这将打破常规expression-东西线(尝试在其中放入一个'^'或'$'并观看火花:-),但这足以满足最初的黑客攻击。 (顺便提一下,'extract_tokens'例程不是我的 - 我在网上发现了它,而且永远感谢那个创建它的人)。

分享和享受。