2012-12-04 4 views
1

주어진 다음의 샘플 문자열이있는 모든 단어를 제목 경우 다음 대문자를 설정합니다 :정규식 혼합 숫자와 문자

PP12111 LOREM IPSUM TM ENCORE 
LOREM PP12111 IPSUM TM ENCORE 
LOREM IPSUM ENCORE TM PP12111 
LOREM PP12111 PP12111 TM ENCORE 

닷넷 정규식 제목 케이스를 설정 한 다음 포함하는 모든 문자열을 변환하는 것입니다 무엇 나는 숫자를 포함하므로 단지 문자열이 제목 케이스로 설정 모든 것을 시작할 수

PP12111 Lorem Ipsum TM Encore 
Lorem PP12111 Ipsum TM Encore 
Lorem Ipsum Encore TM PP12111 
Lorem PP12111 PP12111 TM Encore 

Alternativley와 문자는 대문자로 설정해야합니다 : 대문자로 숫자와 문자 (아래 참고 참조)

Pp12111 Lorem Ipsum TM Encore 
Lorem Pp12111 Ipsum TM Encore 
Lorem Ipsum Encore TM Pp12111 
Lorem Pp12111 Pp12111 TM Encore 

참고 : TM이 변형 된 경우 (tm, Tm, tM) 전체 대문자 여야합니다. TM은 "lorem ipsum TM valor"또는 "lorem ipsum (TM) valor"일 수 있습니다.

다음은 작동하는 순수한 문자열 조작 방법입니다. RegEx 솔루션이 더 적합 할 수 있다고 생각합니까?

private static void Main(string[] args) 
{ 
    var phrases = new[] 
     { 
      "PP12111 LOREM IPSUM TM ENCORE", "LOREM PP12111 IPSUM TM ENCORE", 
      "LOREM IPSUM ENCORE TM PP12111", "LOREM PP12111 PP12111 TM ENCORE", 
     }; 

    Test(phrases); 
} 

private static void Test(IList<string> phrases) 
{ 
    var ti = Thread.CurrentThread.CurrentCulture.TextInfo; 

    for(int i = 0; i < phrases.Count; i++) 
    { 
     string p = ti.ToTitleCase(phrases[i].ToLower()); 
     string[] words = p.Split(' '); 

     for(int j = 0; j < words.Length; j++) 
     { 
      string word = words[j]; 
      if(word.ToCharArray().Any(Char.IsNumber)) 
      { 
       word = word.ToUpper(); 
      } 
      words[j] = word.Replace(" Tm ", " TM ").Replace("(Tm)", "(TM)"); 
     } 

     phrases[i] = string.Join(" ", words); 

     Console.WriteLine(phrases[i]); 
    } 
} 
+0

정규식만으로는이 작업을 수행 할 수 없습니다. 대/소문자를 바꾸려면 콜백 함수가 필요합니다. 'Regex.Replace'의 [this overload] (http://msdn.microsoft.com/en-us/library/ht1sxswy.aspx)를보십시오. –

+0

@ m.buettner - 링크를 제공해 주셔서 감사합니다. 나는 그것을 검토 할 것이고 잘하면 그것이 더 나은 이해를 줄 것이다. –

답변

3

이 같은이 정규식을 사용할 수 있습니다단어 경계입니다.
pos(?!suffix) 접미사 앞자리와 일치하지 않습니다.
\b(?!TM\b)               단어 경계 선행되지 TM 자릿수를 갖지
[A-Z]+                               단어.

Together : 단어 경계 앞에 "TM"이 붙지 않고 그 뒤에 문자 A부터 Z까지 및 단어 경계가옵니다.


업데이트 # 1

상단 케이스 "TM", "Tm은", "tM으로"대문자로 모든 것이 대문자 될 수 있다면

는 모르겠어요. 이 경우 가장 쉬운 해결책은 입력을 대문자로 입력하는 것입니다 : input.ToUpper(). 그렇지 않으면 두 번째 정규식 대체 실행 :

string result = Regex.Replace(result, @"\btm\b", "TM", RegexOptions.IgnoreCase); 

업데이트 # 2

을 당신이 대문자 여러 말을하려는 경우, 당신은 또 다른 경기 평가자 사용할 수 있습니다

MatchEvaluator toUpperCase = m => m.Value.ToUpper(); 
string result = Regex.Replace(result, @"\b(tm|xxx|yyy)\b", toUpperCase, 
           RegexOptions.IgnoreCase); 

tm|xxx|yyy은 대문자로 쓰여질 단어를 지정합니다 ("tm", "xxx"또는 "yyy").

+0

"TM"의 변종 ("LOREM IPSUM ENCORE tm PP12111", "LOREM IPSUM ENCORE tM PP12111"등)에서 형식을 지정하지는 않겠지 만 Regex.Replace (입력 [ ...])를 Regex.Replace (input.ToUpper [...])와 함께 사용하십시오. 당신이 예외를 잡기 위해 많은 단어에 대해 사례없이 효과적으로 전환하는 것처럼 보입니다. 어쩌면 "TM"을위한 2 위일까요? 그러나 그것은 똑같이 우아하지 않습니다. –

+1

환상적! 내 문자열 조작보다 훨씬 깔끔하고 잘 작동합니다. 필자는 7000 가지 항목의 카탈로그를 통해이를 실행했으며 모든 것이 예상대로 포맷 된 것처럼 대략적인 스캔을 수행합니다. 업데이트에 관한 질문 : 대체해야 할 일회성 단어가있을 수 있습니다. 당신 Regex.Replaces 여러 문자열을 함께 할 수 있습니까? –

+0

수축이있는 엣지 케이스가있는 것처럼 보입니다. 즉, '수축이 올바르게 표시되지 않습니다.'가 '수축이 올바르게 대문자로 표시되지 않습니다.' –

-1

첫 번째 : LowerCase 모든 것.

둘째 : 문장을 단어로 나눕니다. 각 단어에 대한

:

확인, 두 문자 또는 문자와 숫자 ([a-z]{2}|[a-z0-9]{2,})

일치가있는 경우 -> 대문자가.

아니요 -> 제목을 지정하십시오.

+0

사례를 두 번 변경하려는 목적은 무엇입니까? 초기 케이스는 최종 결과가 상단인지 제목인지 여부에 영향을주지 않습니다. – Lunyx

+0

you'r 권리 -하지만 MatchGroups 확장 또는 정규식 대/소문자를 구분하는 것을 잊지 마십시오. – dognose

+1

이 아이디어가있는 제안이 있습니다. 제안 된 규칙으로, of, we, us는 모두 대문자로 변환됩니다. – JamieSee

0

이전에 물어 본 가까운 검색 결과는 Regular Expression Uppercase Replacement in C#입니다. 정규 표현식만으로는 충분하지 않습니다. 모든 것을 대문자로 가져 오려면 MatchEvaluator 함수를 작성해야합니다. TM (TM)이 "lorem ipsum TM valor"또는 "lorem ipsum (TM)"일 수있는 경우, 용기"." 나를 당신이 정규식을 모두 고려하는 것을 멈춰야한다고 생각하게 만듭니다. 예전은 어떨까요? 예, 당신은 아마 한 모든 경우를 찾을 수 정규식, 또는 좋은 철저한 matchevaluator를 작성할 수 OA TM 평가 보증 등급 (EAL), 스턴은 TM은 EN 또는 등, 등, 등

그 것이다 논리를 고려하십시오. 그러나 정규 표현식에 익숙하지 않다고 생각하게하는 측면에서 문제를 설명하고 있습니다. 따라서 제게 이것은 당신에게 좋은 대답이라고 생각하는 것이 어렵고 프로덕션에 들어가야하는 것보다 "위험한"해결책이 될 것입니다.

MatchEvaluator evaluator = m => ti.ToTitleCase(m.Value.ToLower()); 
string result = Regex.Replace(input, @"\b(?!TM\b)[A-Z']+\b", evaluator, 
           RegexOptions.IgnoreCase); 

\b                                            :

+0

분명히 RegEx에 익숙하지 않습니다. :) 올리비에의 대답은 좋은 결과물을 만들어 냈습니다. 오트밀에 대한 우려, et. al. 주목 받는다.그러나 TM은 항상 별도의 단어이거나 괄호 안에 있습니다. –

+0

올리버의 대답은 최상이며 받아 들여지는 것을 기쁘게 생각합니다 :) 정규 표현식을 파고 싶다면 골드 스탠다드 책 _ _Mastering Regular Expressions _ http://shop.oreilly.com/product를 확인하십시오. /9780596528126.do –