문제

완벽한 정규식 또는 제목을 취하는 다른 프로세스는 무엇입니까?

<인용구>

Stack Overflow와 같은 URL의 일부가되도록 제목을 어떻게 변경하나요?

로 전환 라코 디스

Stack Overflow의 SEO 친화적 인 URL에 사용 되나요?

내가 사용하는 개발 환경은 Ruby on Rails 이지만 다른 플랫폼이있는 경우 특정 솔루션 (.NET, PHP, Django ),보고 싶습니다. 그들도.

저 (또는 다른 독자)가 다른 플랫폼에서 동일한 문제를 겪게 될 것이라고 확신합니다.

사용자 지정 경로를 사용하고 있으며 주로 모든 특수 문자가 제거되고 모두 소문자이며 모든 공백이 대체되도록 문자열을 변경하는 방법을 알고 싶습니다.

도움이 되었습니까?

해결책

방법은 다음과 같습니다.언뜻 생각하는 것보다 더 많은 가장자리 조건이있을 수 있습니다.

이것은 5 배 더 높은 성능을 위해 펼쳐진 두 번째 버전입니다 (예, 벤치마킹했습니다).이 함수는 페이지 당 수백 번 호출 될 수 있기 때문에 최적화 할 것이라고 생각했습니다. 라코 디스

교체 된 코드의 이전 버전 (기능적으로 동일하고 5 배 더 빠름)을 보려면이 게시물의 업데이트 내역을 확인하세요 (날짜 링크 클릭).

또한 RemapInternationalCharToAscii 메소드 소스 코드는 여기 에서 찾을 수 있습니다.

다른 팁

다음은 Jeff 코드의 내 버전입니다. 다음과 같이 변경했습니다.

  • 하이픈은 추가 할 수있는 방식으로 추가 된 다음 문자열의 마지막 문자이므로 제거해야합니다. 즉, 우리는“my-slug-”를 원하지 않습니다. 이것은이 엣지 케이스에서이를 제거하기위한 추가 문자열 할당을 의미합니다. 지연 하이픈으로이 문제를 해결했습니다. 제 코드를 Jeff의 논리와 비교해 보면 따라하기 쉽습니다.
  • 그의 접근 방식은 순전히 조회 기반이며 Stack Overflow를 조사하는 동안 예제에서 찾은 많은 문자를 놓쳤습니다. 이에 대응하기 위해 먼저 정규화 단계를 수행합니다 (메타 스택 오버플로 질문 전체 (프로필) URL에서 삭제 된 US-ASCII가 아닌 문자 ), 허용 범위를 벗어난 문자는 무시합니다. 대부분의 경우 작동합니다 ...
  • ... 룩업 테이블도 추가해야했습니다. 위에서 언급했듯이 일부 문자는 정규화 될 때 낮은 ASCII 값으로 매핑되지 않습니다. 이것들을 삭제하는 대신, 의심 할 여지없이 허점으로 가득 찬 예외 목록이 있지만 아무것도없는 것보다 낫습니다. 정규화 코드는 Stack Overflow 질문 어떻게 문자열에서 악센트를 제거 할 수 있나요? 에있는 Jon Hanna의 훌륭한 게시물에서 영감을 받았습니다. em>.
  • 이제 대소 문자 변환도 선택 사항입니다.

    public static class Slug
    {
        public static string Create(bool toLower, params string[] values)
        {
            return Create(toLower, String.Join("-", values));
        }
    
        /// <summary>
        /// Creates a slug.
        /// References:
        /// http://www.unicode.org/reports/tr15/tr15-34.html
        /// https://meta.stackexchange.com/questions/7435/non-us-ascii-characters-dropped-from-full-profile-url/7696#7696
        /// https://stackoverflow.com/questions/25259/how-do-you-include-a-webpage-title-as-part-of-a-webpage-url/25486#25486
        /// https://stackoverflow.com/questions/3769457/how-can-i-remove-accents-on-a-string
        /// </summary>
        /// <param name="toLower"></param>
        /// <param name="normalised"></param>
        /// <returns></returns>
        public static string Create(bool toLower, string value)
        {
            if (value == null)
                return "";
    
            var normalised = value.Normalize(NormalizationForm.FormKD);
    
            const int maxlen = 80;
            int len = normalised.Length;
            bool prevDash = false;
            var sb = new StringBuilder(len);
            char c;
    
            for (int i = 0; i < len; i++)
            {
                c = normalised[i];
                if ((c >= 'a' && c <= 'z') || (c >= '0' && c <= '9'))
                {
                    if (prevDash)
                    {
                        sb.Append('-');
                        prevDash = false;
                    }
                    sb.Append(c);
                }
                else if (c >= 'A' && c <= 'Z')
                {
                    if (prevDash)
                    {
                        sb.Append('-');
                        prevDash = false;
                    }
                    // Tricky way to convert to lowercase
                    if (toLower)
                        sb.Append((char)(c | 32));
                    else
                        sb.Append(c);
                }
                else if (c == ' ' || c == ',' || c == '.' || c == '/' || c == '\\' || c == '-' || c == '_' || c == '=')
                {
                    if (!prevDash && sb.Length > 0)
                    {
                        prevDash = true;
                    }
                }
                else
                {
                    string swap = ConvertEdgeCases(c, toLower);
    
                    if (swap != null)
                    {
                        if (prevDash)
                        {
                            sb.Append('-');
                            prevDash = false;
                        }
                        sb.Append(swap);
                    }
                }
    
                if (sb.Length == maxlen)
                    break;
            }
            return sb.ToString();
        }
    
        static string ConvertEdgeCases(char c, bool toLower)
        {
            string swap = null;
            switch (c)
            {
                case 'ı':
                    swap = "i";
                    break;
                case 'ł':
                    swap = "l";
                    break;
                case 'Ł':
                    swap = toLower ? "l" : "L";
                    break;
                case 'đ':
                    swap = "d";
                    break;
                case 'ß':
                    swap = "ss";
                    break;
                case 'ø':
                    swap = "o";
                    break;
                case 'Þ':
                    swap = "th";
                    break;
            }
            return swap;
        }
    }
    

    자세한 내용, 단위 테스트 및 Facebook URL 스키마는 Stack Overflows보다 약간 더 똑똑합니다. 내 블로그의 확장 버전 .

URL 이 컨트롤러를 가리 키도록 사용자 지정 경로를 설정하는 것이 좋습니다.처리해.Ruby on Rails를 사용하고 있으므로 다음은 라우팅 엔진 사용에 대한 소개 입니다.

Ruby에서는 이미 알고있는 정규식이 필요하며 다음은 사용할 정규식입니다. 라코 디스

자바 스크립트 함수를 사용하여 민달팽이 (이 Django 에 기반 / 복사 됨) : 라코 디스

여기에 WordPress의 PHP 기능이 있습니다. WordPress는 멋진 링크를 사용하는 가장 인기있는 플랫폼 중 하나라고 생각합니다. 라코 디스

이 기능과 일부 지원 기능은 wp-includes / formatting.php에서 찾을 수 있습니다.

Rails edge를 사용하는 경우 Inflector.parametrize -다음은 문서의 예입니다. 라코 디스

또한 이전 버전의 Rails에서 악센트 (éphémère)와 같은 이국적인 문자를 처리해야하는 경우 PermalinkFu DiacriticsFu :

라코 디스

Ruby on Rails에 익숙하지 않지만 다음은 PHP 코드입니다.유용하다고 생각되면 Ruby on Rails로 매우 빠르게 번역 할 수 있습니다. 라코 디스

도움이 되었기를 바랍니다.

Ruby 나 Rails에 대해서는별로 관심이 없지만 Perl에서는 다음과 같이합니다. 라코 디스

빠른 테스트를했는데 효과가있는 것 같습니다.루비로 번역하기가 비교적 쉬웠 으면합니다.

모델 클래스에 title 속성이 있다고 가정하면 다음과 같이 모델 내에서 to_param 메소드를 간단히 재정의 할 수 있습니다. 라코 디스

이 Railscast 에피소드 에 모든 세부 정보가 있습니다.다음을 사용하여 제목에 유효한 문자 만 포함되도록 할 수도 있습니다. 라코 디스

아주 오래된 질문이라는 것을 알고 있지만 현재 대부분의 브라우저가 유니 코드 URL을 지원 하기 때문에 XRegex 에서 문자를 제외한 모든 것을 변환하는 훌륭한 솔루션을 찾았습니다 (모든 언어에서'-').

여러 프로그래밍 언어로 수행 할 수 있습니다.

패턴은 \\p{^L}+이며 문자가 아닌 모든 것을 '-'로 바꾸는 데 사용하면됩니다.

xregex 모듈을 사용하는 node.js의 작업 예 라코 디스

Ruby의 Brian 코드 : 라코 디스

downcase는 문자열을 소문자로 바꾸고, strip는 선행 및 후행 공백을 제거하고, 첫 번째 gsub 호출은 g lobally sub 로 공백을 지정하고 두 번째는 공백을 모두 제거합니다.문자 나 대시가 아닙니다.

PermalinkFu 라는 작은 Ruby on Rails 플러그인이 있습니다.이렇게합니다. 이스케이프 메서드 는 다음과 같은 문자열로 변환합니다. URL 에 적합합니다.코드를 살펴보십시오.그 방법은 아주 간단합니다.

ASCII 가 아닌 문자를 제거하려면 iconv lib를 사용하여 'ascii // ignore // translit 'from'utf-8 '.그런 다음 공백이 대시로 바뀌고 모든 것이 다운 케이스로 표시됩니다.

다음 도우미 방법을 사용할 수 있습니다.유니 코드 문자를 변환 할 수 있습니다. 라코 디스

다음은 Jeff 코드의 (느리지 만 작성하기 재미있는) 버전입니다. 라코 디스

내 테스트 문자열 :

" I love C#, F#, C++, and... Crème brûlée!!! They see me codin'... they hatin'... tryin' to catch me codin' dirty... "

stackoverflow 솔루션 훌륭하지만 최신 브라우저 (평상시처럼 IE 제외)는 이제 utf8 인코딩을 멋지게 처리합니다.

여기에 이미지 설명 입력

그래서 제안 된 솔루션을 업그레이드했습니다. 라코 디스

Pastebin의 전체 코드

수정 : 다음은 RemapInternationalCharToAscii 메소드에 대한 코드 입니다 (pastebin에 없음).

정규식 을 사용하지 않고 수행되는 방식이 마음에 들었 기 때문에 PHP로 포팅했습니다..문자를 확인하기 위해 is_between라는 함수를 추가했습니다. 라코 디스

이제 모든 브라우저가 utf8 인코딩을 훌륭하게 처리하므로 WebUtility.UrlEncode 메서드, 유사 HttpUtility.UrlEncode 는 @giamin에서 사용하지만 웹 애플리케이션 외부에서 작동합니다.

아니요, 아니요. 당신은 모두 매우 틀 렸습니다. 분음 부호를 제외하고는 거기에 도달했지만 아시아 문자는 어떻습니까 (루비 개발자는 nihonjin 형제).

Firefox와 Safari는 모두 URL 에 비 ASCII 문자를 표시하며 솔직히 보입니다. 큰. ' http://somewhere.com/news/read/ お 前 た ち は ア ホ じ ゃ な い か い '.

여기에이를 수행 할 PHP 코드가 있습니다.하지만 방금 작성했고 스트레스 테스트를 거치지 않았습니다. 라코 디스

예 : 라코 디스

출력 : 코린과 토마스와 아 노르 드

'-and-'는 &가 '-and-'로 변경되기 때문입니다.

코드를 TypeScript로 포팅했습니다.JavaScript에 쉽게 적용 할 수 있습니다.

최신 브라우저 또는 ES6를 대상으로하는 경우 .contains를 대신 사용할 수 있습니다. 라코 디스

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top