2014-03-29 5 views
1

정규식을 처음 접해 보았습니다.Regex 수량 한정자

다음 예제에서는 facebook.com/pages/Dr-Morris-Westfried-Dermatologist/176363502456825?id=176363502456825&sk=info을 추출하려고합니다. 나는 게으른 한정어와 lookbehinds에 대해 읽었지만 여전히 올바른 정규 표현식을 만들 수는 없다. 나는 facebook.com\/.*?sk=info이 작동 할 것으로 기대하지만 너무 많이 캡처합니다. 너희들도 도와 줄 수 있니?

<i class="mrs fbProfileBylineIcon img sp_2p7iu7 sx_96df30"></i></span><span class="fbProfileBylineLabel"><span itemprop="address" itemscope="itemscope" itemtype="http://schema.org/PostalAddress"><a href="https://www.facebook.com/pages/Dr-Morris-Westfried-Dermatologist/176363502456825?sk=page_map" target="_self">7508 15th Avenue, Brooklyn, New York 11228</a></span></span></span><span class="fbProfileBylineFragment"><span class="fbProfileBylineIconContainer"><i class="mrs fbProfileBylineIcon img sp_2p7iu7 sx_9f18df"></i></span><span class="fbProfileBylineLabel"><span itemprop="telephone">(718) 837-9004</span></span></span></div></div></div><a class="title" href="https://www.facebook.com/pages/Dr-Morris-Westfried-Dermatologist/176363502456825?id=176363502456825&amp;sk=info" aria-label="About Dr. Morris Westfried - Dermatologist"> 
+3

파이썬에서 HTML 파서를 검색하십시오. – hjpotter92

+0

http://stackoverflow.com/a/1732454/2823755 – wwii

답변

2

는 왜 패턴이 작동하지 않습니다

당신의 패턴이 작동하지 않습니다 정규식 엔진 시도 때문에 귀하의 패턴 왼쪽에서 오른쪽 문자열에서.

sk=info을 찾을 때까지 정규식 엔진이 문자열의 첫 번째 facebook.com\/을 충족하고 후 .*?을 사용하기 때문에, 정규식 엔진이 (수) 경기 결과 (" 또는 > 또는 공백을 포함하여) 모든 문자를 추가합니다

( .은 개행을 제외한 모든 문자와 일치 할 수 있기 때문에).

fejese가 점을 [^"]으로 바꾸거나 aliteralmind가 [^>]으로 바꾸고 첫 번째 문자열에서이 위치에서 패턴이 실패하도록 제안하는 이유입니다.

html을 처리하려는 경우 html 파서를 사용하는 것이 가장 쉬운 방법입니다.그러나 성 일치 또는 검색/바꾸기의 경우 html 파서가 보안 성, 단순성을 제공하면 단일 작업에 대해 문서의 전체 트리를로드해야하기 때문에 성능 측면에서 비용이 발생합니다.

2

문제는 다른 facebook.com 부분이 있다는 것입니다. 당신은 그래서 하나 개의 속성 내에서 유지하는 데 필요한 .*" 일치하지 않는 제한 할 수 있습니다 만 .*으로

facebook\.com\/[^"]*;sk=info 
+0

좋은 지점, 고정 – fejese

+0

글자 물음표로 작동하지 않습니다. 내 대답 아래의 의견을 읽으십시오. – aliteralmind

3

이 작동 :)

facebook\.com\/[^>]*?sk=info 

Regular expression visualization

Debuggex Demo

먼저을 찾습니다. facebook.com을 입력 한 다음 sk=info까지 계속합니다. 사이에 또 ​​다른 facebook.com이 있기 때문에 중복됩니다. 당신이하지을 그 사이의 독특한 것은이 원하는

그렇게 아무것도   > 아무것도하지만  에 facebook.com가장 가까운를 찾아 변경 (다른 문자들, 또는 <)를 >입니다 원하는대로 sk=info으로 이동하십시오.

예, HTML 용 정규식은 기본 작업에서만 사용해야합니다. 그렇지 않으면 파서를 사용하십시오.

+0

debuggex로 이동하십시오. 그것은 작동합니다. '?'는 필요하지 않을 수도 있지만 작동합니다. 그것은'[^>] *?의 일부로, 0 개 이상의 *'''characaters가 아니라, 의미가 있습니다. 그것은 규칙적인 '?'이 아니며, 소유 수정자입니다. – aliteralmind

+0

충분히 공정하게; 그것은 소극적인 것이지 소유욕이 아니라 그것을 사용하는 것에 대한 명성입니다. :) –

+0

"릴럭 터트". 권리. 소유욕이 없다. – aliteralmind

4

내가 정규식을 사랑하는이는 HTML 구문 분석 작업입니다만큼 :

>>> from bs4 import BeautifulSoup 
>>> html = .... # that whole text in the question 
>>> soup = BeautifulSoup(html) 
>>> pred = lambda tag: tag.attrs['href'].endswith('sk=info') 
>>> [tag.attrs['href'] for tag in filter(pred, soup.find_all('a'))] 
['https://www.facebook.com/pages/Dr-Morris-Westfried-Dermatologist/176363502456825?id=176363502456825&sk=info'] 
+0

계속 진행하는 것이 더 좋은 방법 일 수는 있지만 패턴이 작동하지 않는 이유에 대해서는 설명하지 않습니다. –

+0

@CasimiretHippolyte 질문에 "나는 추출하고 싶다 ..."; 그게 위의 것입니다. 또한 [this] (https://meta.stackexchange.com/questions/66377/what-is-the-xy-problem)와 관련이 있습니다. –

+0

@CasimiretHippolyte - 정규식 설명에 대해 많은 감사드립니다. 나는 비슷한 일을 위해 BeautifulSoup를 사용했다. – Peter