가장 짧은 고유 부분 문자열


29

입력

영숫자 문자열 s입니다.

산출

에서 (연속적인) 하위 문자열로 정확히 한 번 발생하는 가장 짧은 문자열입니다 s. 중복 발생은 별개의 것으로 계산됩니다. 길이가 같은 후보가 여러 개있는 경우 모든 후보를 발생 순서대로 출력해야합니다. 이 도전에서, 빈 n + 1문자열은 length의 문자열에서 시간이 발생합니다 n.

문자열을 고려

"asdfasdfd"

빈 문자열은 10 번 발생하므로 고유 한 발생의 후보가 아닙니다. 문자의 각각은 "a", "s", "d", 그리고 "f"그들이 후보 중 하나되지 않도록, 두 번 이상 발생합니다. 부분 캐릭터 "fa""fd"길이 2의 다른 모든 문자열이 두 번 발생하는 동안, 한 번만이 순서대로 발생합니다. 따라서 올바른 출력은

["fa","fd"]

규칙

기능과 전체 프로그램이 모두 허용되며 표준 허점은 허용되지 않습니다. 출력의 정확한 형식은 이유 내에서 유연합니다. 특히 빈 문자열에 대한 출력을 생성하지 않아도되지만 오류를 던지는 것은 불가능합니다. 가장 낮은 바이트 수가 이깁니다.

테스트 사례

"" -> [""]
"abcaa" -> ["b","c"]
"rererere" -> ["ererer"]
"asdfasdfd" -> ["fa","fd"]
"ffffhhhhfffffhhhhhfffhhh" -> ["hffff","fffff","hhhhh","hfffh"]
"asdfdfasddfdfaddsasadsasadsddsddfdsasdf" -> ["fas","fad","add","fds"]

리더 보드

제가 약속 한 언어 별 리더 보드입니다.

답변이 표시되도록하려면 다음 마크 다운 템플릿을 사용하여 헤드 라인으로 답변을 시작하십시오.

# Language Name, N bytes

N제출물의 크기는 어디에 있습니까 ? 당신이 당신의 점수를 향상시킬 경우에, 당신은 할 수 있습니다 를 통해 눈에 띄는에 의해, 헤드 라인에 오래된 점수를 유지한다. 예를 들어 :

# Ruby, <s>104</s> <s>101</s> 96 bytes

<script src='https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js'></script><script>site = 'meta.codegolf',postID = 5314,isAnswer = true,QUESTION_ID = 45056;jQuery(function(){var u='https://api.stackexchange.com/2.2/';if(isAnswer)u+='answers/'+postID+'?order=asc&sort=creation&site='+site+'&filter=!GeEyUcJFJeRCD';else u+='questions/'+postID+'?order=asc&sort=creation&site='+site+'&filter=!GeEyUcJFJO6t)';jQuery.get(u,function(b){function d(s){return jQuery('<textarea>').html(s).text()};function r(l){return new RegExp('<pre class="snippet-code-'+l+'\\b[^>]*><code>([\\s\\S]*?)<\\/code><\/pre>')};b=b.items[0].body;var j=r('js').exec(b),c=r('css').exec(b),h=r('html').exec(b);if(c!==null)jQuery('head').append(jQuery('<style>').text(d(c[1])));if (h!==null)jQuery('body').append(d(h[1]));if(j!==null)jQuery('body').append(jQuery('<script>').text(d(j[1])))})})</script>


조합 내장 함수에 제한이 있습니까?
Martin Ender

3
@ MartinBüttner이 도전에서는 모든 것이 진행됩니다. 이것이 충분한 답변을 얻는다면, 나는 언어 별 리더 보드를 만들 것입니다. 따라서 장비가 부족한 언어조차도 의미있는 경쟁을 할 수 있습니다.
Zgarb

당신이 사용 하시겠습니까 내 코드 골프 리더 조각을 ? 그런 다음 리더 보드를 최신 상태로 유지하기 위해 모든 수정 사항을 모니터링 할 필요는 없습니다. 그렇게하면 추가 할 수 있으며 헤더 형식과 일치하도록 답변을 진행합니다.
Martin Ender

@ MartinBüttner 감사합니다, 감사합니다!
Zgarb

다 했어요! 작동하지 않는 경우 알려주십시오. (미래에 도전하기 위해 무료로 재사용하십시오.)
Martin Ender

답변:


3

Pyth, 27 26 바이트

&zhfTmf!/>zhxzYYm<>zkdUzUz

여기에서 시도하십시오.

온라인 컴파일러의 버그로 인해 빈 문자열 대소 문자는 명령 행 버전에서만 올바르게 작동합니다 .

온라인 컴파일러의 입력으로 줄 바꿈을 제공하여 버그를 치료할 수도 있습니다.

설명:

                                   z = input(), implicit.
&z                                 Prints empty string if input is empty.
  hfT                              Take the first non-empty list from
     m                  Uz         A list of list of substrings of z, divided by length
                m<>zkdUz           with some shorter strings repeated later, to no effect.
      f                            Where the substrings are filtered on
       !/      Y                   There being 0 occurrences of the substring in
         >z                        The slice of z
           hxzY                    from the character after the first character
                                   of the first occurrence of the substring in z
                                   to the end of z.

빈 문자열 입력에 실패합니다.
Optimizer

@Optimizer 실제로 온라인 컴파일러의 버그라고 생각합니다. 명령 행 버전에서 작동합니다. 실제로 z온라인에서 입력이 실패하지 않으므로 인터프리터의 버그입니다.
isaacg

EOF를 제공하지 않습니까?
Optimizer

@Optimizer Pyth는 줄 바꿈 종료 입력을 예상하며 이는 잘못된 일입니다.
isaacg

빈 문자열을 전달하는 것도 가능하지 않습니까?
Optimizer

13

파이썬 3 124 123 111 96 바이트

f=lambda s,n=1:[x for x in[s[i:i+n]for i in range(len(s)+1)]if s.find(x)==s.rfind(x)]or f(s,n+1)

왼쪽에서 첫 번째 항목이 오른쪽에서 첫 번째 항목과 같도록 문자열을 찾습니다. +1에서는 range빈 문자열 케이스를 수용하는 것입니다.

이제 파이썬 만 중복 일치 하는 .count()것을 계산 했다면 이것은 조금 짧았을 것입니다.


6

매스 매 티카, 95 94 79 바이트

Cases[Tally@StringCases[#,___,Overlaps->All],{s_,1}:>s]~MinimalBy~StringLength&

StringCases가능한 모든 하위 문자열을 가져오고 두 번 이상 나타나는 문자열 TallyCases필터링하여 MinimalBy가장 짧은 문자열을 찾습니다.


&코드 끝에 여분이 없습니까?
David G. Stork

당신은 빠릅니다!
David G. Stork

4

GolfScript, 44 바이트

:S;-1:x{;S,x):x-),{S>x<}%:^1/{^\/,2=},.!}do`

stdin에서 문자열로 입력을 가져오고 이중 배열 구문으로 출력합니다 (예 :) [["b"] ["c"]]. 온라인 데모

해부

:S;          # Store input in S and pop it
-1:x         # Store -1 in x
{            # do-while loop
  ;          #   Pop x the first time and [] every subsequent time
  S,x):x-),  #   Increment x and build an array [0 1 ... len(S)-x]
  {S>x<}%    #   Map that array to [substr(S,0,x) substr(S,1,x) ...]
  :^         #   Store in ^ (to avoid the token coalescing with the next char)
  1/         #   Split by length 1 to iterate over 1-elt arrays rather than strings
  {^\/,2=},  #   Filter to arrays which occur exactly once as a subarray of ^
  .!         #   Duplicate and test emptiness
}do          # end do-while loop: loop if the filtered array is empty
`            # Stringify for output

이것은 빈 문자열 (위의 링크 된 온라인 데모에서 테스트 케이스로 포함)에 특별한 경우가 필요하지 않도록 배열됩니다.


3

CJam, 52 43 40 바이트

]]q:Q,,{)Q,1$-),f{Q><}:R{R\a/,2=},}%{}=p

입력은 따옴표없는 문자열입니다

설명 :

]]                                       "For empty string input case";
  q:Q                                    "Read the input and store in Q";
     ,,                                  "Take length of input and 0 to length array";
       {                          }%     "Map the above array on this code block";
        )Q                               "Increment the number in the current iteration, L";
         Q,1$                            "Take input's length and copy the above number";
             -)                          "Get upper limit of next loop to get substrings";
               ,f{   }                   "Get 0 to above number array and for each";
                  Q><                    "Get the L length substring at Ith index where";
                                         "I loops from 0 to Q, - L + 1";
                      :R                 "Store this list of substring of length L in R";
                        {R\a/,2=},       "Filter to get unique substrings";
                                    {}=  "Get the first non empty substring array";
                                         "This leaves nothing on stack if all are empty";
                                       p "Print the top stack element. At this point, its";
                                         "Either the first non empty substring array or";
                                         "the ]] i.e. [""] which we added initially";

예:

asdfdfasddfdfaddsasadsasadsddsddfdsasdf

산출

["fas" "fad" "add" "fds"]

여기에서 온라인으로 사용해보십시오


3

스칼라, 120 바이트

readLine.inits.flatMap(_.tails).toList.groupBy(l=>l).filter(x=>x._2.length<2).map(_._1).groupBy(_.length).minBy(_._1)._2

나는 적어도 이미 트윗에 맞는 140으로 시작했습니다.

(                                        // added for comments
 readLine                                // input
.inits.flatMap(_.tails).toList           // get all substrings of that string
.groupBy(l=>l).filter(x=>x._2.length<2)  // remove substrings that occur more than once
.map(_._1).groupBy(_.length)             // take the substring and group by length
.minBy(_._1)._2                          // take the list of shortest substrings
)

궁금해? 왜 (_)대신 신원으로 작동 하지 l=>l않습니까?
자부심을 가진 haskeller

나도 궁금하다. 어떻게 든 list.groupBy(_)동일합니다 x => list.groupBy(x). 왜 그렇게 구현했는지 모르겠습니다.
Dominik Müller

3

자바 스크립트 (ES6) 109 110

입력 문자열이 영숫자이므로 indexOf 대신 검색을 편집하십시오 . 감사합니다 @IsmaelMiguel

재귀 함수, 길이 1로 시작하여 올라가는 하위 문자열을 찾습니다.

F=(s,n=1,r)=>
s?[...s].map((a,i)=>~s.indexOf(a=s.substr(i,n),s.search(a)+1)?r:r=[...r||[],a])&&r||F(s,n+1):[s]

언 골프 및 설명

 F = function(s, n=1) { // start with length 1
   var i, a, p, r;
   if (s == "") // special case for empty input string
     return [s];
   for (i = 0; i < s.length; i++) 
   // for each possibile substring of length n
   // (should stop at s.length-n+1 but going beyond is harmless)
   // Golfed: "[...s].map((a,i)" ... using i, a is overwrittem
   {
     a = s.substr(i, n); // substring at position i
     p = s.search(a); // p is the first position of substring found, can be i or less
     p = s.indexOf(a, p + 1) // p is now the position of a second instance of substring, or -1 if not found
     if (~p) // ~p is 0 if p is -1
     {
       ; // found more than once, do nothing
     }
     else
     {
       r = r || []; // if r is undefined, then it becomes an empty array
       r.push(a); // save substring 
       // Golfed: "r=[...r||[],a]"
     }
   }
   if (r) // if found some substring, saved in r
   {
     return r;
   }
   return F(s, n+1) // recursive retry for a bigger length
 }

FireFox / FireBug 콘솔에서 테스트

;["", "abcaa", "rererere", "asdfasdfd", "ffffhhhhfffffhhhhhfffhhh", 
 "asdfdfasddfdfaddsasadsasadsddsddfdsasdf"]
.forEach(x=>console.log(x,F(x)))

산출

 [""]
abcaa ["b", "c"]
rererere ["ererer"]
asdfasdfd ["fa", "fd"]
ffffhhhhfffffhhhhhfffhhh ["hffff", "fffff", "hhhhh", "hfffh"]
asdfdfasddfdfaddsasadsasadsddsddfdsasdf ["fas", "fad", "add", "fds"]

.search대신 사용 .indexOf하면 2 바이트를 절약 할 수 있습니다.
Ismael Miguel

@IsmaelMiguel no 1) 검색에는 오프셋 매개 변수가 없습니다. 2) 검색에는 정규 표현식이 필요하며. * []와 같은 특수 문자로 실패합니다.
edc65

1
그러나 처음에는 안전하게 (을 s.indexOf(a)+1) 교체 할 수 있습니다 . 그것은 화제가되지만 그 문자와는 작동하지 않지만 걱정할 필요는 없습니다! OP 인용 : " Input: An alphanumeric string s."
Ismael Miguel

@IsmaelMiguel, 감사합니다. '영숫자'구속 조건을
놓치다

1
@IsmaelMiguel 나는 방법을 찾지 못했다 ... 나는 진실하거나 허위가 필요하며 어떤 배열 (비어있는 [])은 자바 스크립트에서 진실한 가치이다
edc65

3

자바, 168 168176233

다음은 매우 기본적인 중첩 루프 예제입니다.

void n(String s){for(int l=0,i=0,t=s.length(),q=0;l++<t&q<1;i=0)for(String b;i<=t-l;)if(s.indexOf(b=s.substring(i,i+++l),s.indexOf(b)+1)<0){System.out.println(b);q++;}}

또는 더 읽기 쉽습니다.

void t(String s){
    for(int l=0,i=0,t=s.length(),q=0;l++<t&q<1;i=0)
        for(String b;i<=t-l;)
            if(s.indexOf(b=s.substring(i,i++ +l),s.indexOf(b)+1)<0){
                System.out.println(b);
                q++;
            }
}

당신은 가독성, 분할을 원하는 경우에 +++그것의 여부를 표시하도록 + ++하거나 ++ +도움이 될 것이다 ... 그리고 당신은 몇 바이트를 저장하려는 경우, 초기화하는하여 해당 할 수있는 방법이있을 수 있습니다 q=1, 교체 q++q=t, 및 교체 l++<t&q<1와 같은 뭔가 t>l+=q. 아마도 하나 또는 두 개의 다른 오프셋을 조정해야 작동 할 수 있습니다.
피터 테일러

@Peter 글쎄, 읽을 수 있음으로 나는 주로 "수평으로 스크롤 할 필요가 없다"는 것을 의미했지만 +++. 나는 그것을 조정하려고 노력했지만 (특히 q, 다소 낭비되는 느낌이 들지만) 아직 견고한 것을 찾지 못했습니다.
Geobits

@PeterTaylor Java의 어휘 규칙으로 인해 +++항상로 해결됩니다 ++ +.
FUZxxl

@FUZxxl, 나는 대부분의 Java 사용자조차도 그것을 알고 있으며,이 사이트에는 Java를 모르는 사람들이 많이 있습니다.
피터 테일러

1
lastIndexOf 대신 오프셋으로 indexOf를 사용하면 1 바이트를 잘라야합니다 (자바 스크립트 답변 참조)
edc65

3

하스켈 169 162 155 153 151 138 120 115

import Data.List
l=length
q k=filter$(==)k.l
p y=q(minimum.map l$y)$y
f x=p$concat$q 1$group$sort$(tails x>>=inits)

그것을 사용하려면 :

f "asdfdfasddfdfaddsasadsasadsddsddfdsasdf"

다음을 제공합니다.

["add","fad","fas","fds"]

Btw. 내 코드의 마지막 줄을 싫어합니다 (반복 h y). 그것을 제거 할 힌트가 있습니까?


1
어떻게 정의 해야합니까 ( g y=q(minimum.(map l)$y)$y괄호가 map l정말로 필요합니까?) f=g.concat.q 1.group.sort.concatMap inits.tails?
FUZxxl

1
사용 >>=대신에 concatMap, 즉 f x=p$concat$q 1$group$sort$(tails x>>=inits)2 바이트를 저장합니다. 왜 Data.Ord수입?
nimi

1
의 괄호는 q당신이 쓸 수 있기 때문에, 불필요 filter$(==)k.l, 같은 마지막이다 $하고 전 공간 y에들 p. 반입 후 세미콜론을 제거 할 수도 있습니다 ( Data.Ord실제로 불필요한 것 같습니다).
Zgarb

Leksah 컴파일러는 $공백이 아닌 뒤에 허용하지 않습니다 . 약간의 바이트를 삭감하지만 언어 사양에 있습니까?
RobAu

1
GHC가 수락합니다.
Zgarb

3

J, 61 58 44 42 40 38 37 바이트

[:>@{.@(#~#@>)#\<@(~.#~1=#/.~)@(]\)]

다음은 솔루션의 개별 구성 요소로 분할 된 버전입니다.

unqs =. ~. #~ 1 = #/.~               NB. uniques; items that appear exactly once
allsbsq =. #\ <@unqs@(]\) ]        NB. all unique subsequences
shrtsbsq =. [: >@{.@(#~ #@>) allsbsq NB. shortest unique subsequence
  • x #/. yx에서 발생 빈도의 각 개별 요소에 대해 계산 합니다 y. 이것을로 사용하면 개수의 y #/. y각 개별 요소에 대해를 얻습니다 y. 예를 들어, a #/. a에 대한 a =. 1 2 2 3 4 4수익률 1 2 1 2.
  • 1 = y의 항목 y이 같은지 확인합니다 1. 예를 들어 1 = a #/. a수확량1 0 1 0 입니다.
  • u~모나 딕 동사 의 반사 입니다 u. 이것은와 u~ y동일합니다 y u y. 따라서 #/.~ y와 동일합니다 #/.~ y. 이완 동사에 적용될 때 u~수동적 입니다 u. 즉와 x u~ y같습니다 y u x. 이것들은 내가 명시 적으로 언급하지 않은 다른 몇 곳에서 사용됩니다.
  • ~. y는 IS 너브y제거 중복 갖는 벡터. 예를 들어 ~. ayields 1 2 3 4입니다.
  • x # y( 사본 ) y은 색인의 항목에서 선택합니다 .x 포함하는 합니다 1.
  • 따라서 한 번만 나타나는 (1 = y #/. y) # (~. y)요소로 구성된 벡터를 만듭니다 y. 암묵적 표기법에서이 동사는 다음과 같이 쓰여집니다 ~. #~ 1 = #/.~. 이 문구를 불러 봅시다unqs나머지 설명을 를 .
  • x ]\ y을 생성 x하여 1 + y - x모든 배열 infixes 벡터의 y길이 x. 예를 들어 3 ]\ 'asdfasdfd수확량

    asd
    sdf
    dfa
    fas
    asd
    sdf
    dfd
    
  • # y는 IS 탈리y인, 요소의 수는 y.

  • u\ yu접두사 에 적용됩니다 y. 또한 #\ y에서에서 1로 정수 벡터를 만듭니다 #y.
  • < y 넣다 y상자에 습니다. 배열은 비정형 일 수없고 길이가 다른 접미사 배열을 계산하기 때문에 필요합니다. 박스형 배열은 스칼라로 계산됩니다.
  • 따라서 정확히 한 번 발생하는 y 의 길이 k (모두 0 ≤ k < ) (i. # y) <@:unqs@(]\) y#y박스형 배열로 구성된 벡터를 생성합니다 . 이 동사의 암묵적인 형태는 또는 우리가 사용하지 않는 경우 이름을. 이 설명의 나머지 부분에 대해이 문구 를 호출합시다 . 예를 들어 수율은 다음과 같습니다.#yi.@# <@unqs@(]\) ]i.@# <@(~. #~ 1 = #/.~)@(]\) ]unqsallsbsqallsbsq 'asdfasdfd'

    ┌┬─┬──┬───┬────┬─────┬──────┬───────┬────────┐
    ││ │fa│dfa│sdfa│asdfa│asdfas│asdfasd│asdfasdf│
    ││ │fd│fas│dfas│sdfas│sdfasd│sdfasdf│sdfasdfd│
    ││ │  │dfd│fasd│dfasd│dfasdf│dfasdfd│        │
    ││ │  │   │sdfd│fasdf│fasdfd│       │        │
    ││ │  │   │    │asdfd│      │       │        │
    └┴─┴──┴───┴────┴─────┴──────┴───────┴────────┘
    
  • (#@> y) # yy비어 있지 않은 박스형 배열의 벡터에서 가져옵니다 .

  • {. yvector의 첫 번째 요소를 사용 y합니다.
  • > y 상자를 제거합니다 y .
  • 따라서 > {. (#@> y) # y박스형 배열의 벡터에서 언 박스형 첫 번째 비어 있지 않은 배열을 생성합니다 y. 이 문구는 >@{.@(#~ #@>)암묵적인 표기법으로 작성 되었습니다.
  • 마지막으로, 우리가 가진 문제에 대한 해결책을 만들기 [: >@{.@(#~ #@>) allsbsq위해 이전 문구를 조립합니다 allsbsq. 공백이 포함 된 전체 문구는 다음과 같습니다.

    [: >@{.@(#~ #@>) i.@# <@(~. #~ 1 = #/.~)@(]\) ]
    

2

하스켈, 135 바이트

import Data.List
f ""=[""]
f g=map(snd)$head$groupBy(\a b->fst a==fst b)$sort[(length y,y)|[y]<-group$sort[x|x@(_:_)<-tails g>>=inits]]

2

PHP, 171 (152) 134 125

function f($s){while(!$a&&++$i<strlen($s))for($j=0;$b=substr($s,$j++,$i);)strpos($s,$b)==strrpos($s,$b)&&($a[]=$b);return$a;}

http://3v4l.org/RaWTN


명시 적으로 정의 할 필요는 없습니다. $j=0 . 앞서 있습니다 substr($s,$j++,$i). 을 정의하지 않으면 $j이를 다시 쓸 수 substr($s,0+$j++,$i)있고 2 바이트를 절약 할 수 있습니다 . 왜 그런가요? 글쎄, 처음 $j이 될 것입니다 null. 그리고 당신은 효과적으로 통과 nullsubstr것입니다. 사용 0+$j++변환됩니다 null0. 필요하지 않은 것으로 보이면 필요없이 계속 진행하여 $j=0부품을 제거하십시오 .
Ismael Miguel

그것을 시도했다; PHP에는 강력한 범위가 없기 때문에 작동하지 않으므로 루프의 $j각 반복마다 지워지고 다시 초기화되지 않습니다 while(). 따라서 처음에는 null이지만 (따라서 호출 에 0의해 변환 될 것입니다. $j++), 나중에 외부 루프의 반복에서는 이전 값으로 유지됩니다. 초기화만큼 그렇게 초기화되지는 않습니다. 제안 해 주셔서 감사합니다 :-)
Stephen

여기에서는 141 바이트 길이의 솔루션을 제공합니다. function f($s){$l=strlen($s);while(!$a&&++$i<$l)for($j=0;$j<$l;)($b=substr($s,$j++,$i))&(strpos($s,$b)==strrpos($s,$b)&&($a[]=$b));return$a;}변경 사항 : 모두 제거 하고 한 장소 대신 ||1비트 단위 &( AND)를 사용 하고 (2 바이트 절약) 외부 &&$j<$l&&[...]부품을 이동하고 for불필요한 괄호를 제거했습니다.
Ismael Miguel

1
하나 (134)는 긴 선물 바이트 : function f($s){$l=strlen($s);while(!$a&&++$i<$l)for($j=0;$j<$l;)strpos($s,$b=substr($s,$j++,$i))==strrpos($s,$b)&&($a[]=$b);return$a;}변경 이전 코드를 만든 다음 이동 $b=substr($s,$j++,$i)strpos($s,$b)를 만들고 strpos($s,$b=substr($s,$j++,$i)), 더 불필요한 parenthesys을 제거하고 불필요한을 제거 &.
Ismael Miguel

1
관리 좀 더 자르고 :-) substr($s,$j++,$i)반환 ""할 때 $j도달하는 문자열의 길이, false그 후, 그 할당은 또한 루프 조건 휴식이 될 수 있습니다. 그런 다음 한 번만 사용 $l하면 통합 할 수 있습니다.
Stephen

2

Groovy (Oracle 구현에 대한 Java 정규식), 124

c={m=it=~/(?=(.*?)(?=(.*))(?<=^(?!.*\1(?!\2$)).*))/;o=m.collect({it[1]});o.findAll({it.size()==o.min({it.size()}).size()});}

Groovy 2.4 + Oracle JRE 1.7에서 테스트되었습니다. 위의 코드가 작동하도록하는 버그가 수정되지 않았기 때문에 정규식은 Java 6에서 Java 8에 대해 작동해야합니다. Java 5에는 Java 6에서 수정 된 Look-Behind 버그가 있으므로 이전 버전에 대해서는 확실하지 않습니다.

정규 표현식은 입력 문자열의 모든 위치에서 다른 곳에 중복 하위 문자열이없는 가장 짧은 문자열을 찾습니다. 외부 코드는 필터링을 처리합니다.

(?=(.*?)(?=(.*))(?<=^(?!.*\1(?!\2$)).*))
  • 문자열이 겹칠 수 있으므로 전체를 둘러 봅니다 (?=...).
  • (.*?) 가장 짧은 부분 문자열에서 검색
  • (?=(.*)) 문자열의 나머지 부분을 캡처하여 현재 위치를 표시합니다.
  • (?<=^(?!.*\1(?!\2$)).*)가변 길이 look-behind의 에뮬레이션으로 (?<=.*), 길이 검사를 통과 할 수있는 구현 버그를 활용합니다 .
  • (?!.*\1(?!\2$))다른 곳에서 동일한 하위 문자열을 찾을 수 없는지 확인합니다. 그만큼(?!\2$) 문자열이 일치 원래 위치를 거부한다.

    외부 둘러보기 구성의 제한은 중첩 된 둘러보기 구성에 적용되지 않습니다. 따라서 중첩 된 네거티브 룩어 헤드 (?!.*\1(?!\2$))는 룩 앤비의 오른쪽 경계까지가 아니라 전체 문자열을 실제로 확인합니다.


2

리볼, 136 바이트

f: func[s][repeat n length? b: copy s[unless empty? x: collect[forall s[unless find next find b t: copy/part s n t[keep t]]][return x]]]

언 골프 드 :

f: func [s] [
    repeat n length? b: copy s [
        unless empty? x: collect [
            forall s [
                unless find next find b t: copy/part s n t [keep t]
            ]
        ][return x]
    ]
]

사용 예 :

>> f ""       
== none

>> f "abcaa"
== ["b" "c"]

>> f "rererere"
== ["ererer"]

>> f "asdfasdfd"
== ["fa" "fd"]

>> f "ffffhhhhfffffhhhhhfffhhh"
== ["hffff" "fffff" "hhhhh" "hfffh"]

>> f "asdfdfasddfdfaddsasadsasadsddsddfdsasdf"
== ["fas" "fad" "add" "fds"]


NB. 코드의 핵심은 find부품의 작동 방식이라고 생각합니다 . 잘하면 이것이 설명하는 데 도움이 될 것입니다 ...

>> find "asdfasdfd" "df"
== "dfasdfd"

>> next find "asdfasdfd" "df"
== "fasdfd"

>> find next find "asdfasdfd" "df" "df"
== "dfd"

>> ;; so above shows that "df" is present more than once - so not unique
>> ;; whereas below returns NONE because "fa" found only once - ie. bingo!

>> find next find "asdfasdfd" "fa" "fa"
== none

1

하스켈, 119

f s=[r|n<-[1..length s],l<-[map(take n)$take(length s-n+1)$iterate(drop 1)s],r<-[[j|j<-l,[j]==[r|r<-l,r==j]]],r/=[]]!!0

당신은 q = length어딘가에 넣고 사용할 수 있고 q, 약간의 바이트를 줄입니다
RobAu

1

Brachylog , 10 바이트

sᶠ≡ᵍ~gˢlᵍt

온라인으로 사용해보십시오!

sᶠ            The list of every substring of the input
  ≡ᵍ          grouped by identity,
    ~gˢ       with length-1 groups converted to their elements and other groups discarded,
       lᵍ     and grouped by their length,
         t    has the output as its last group.

하지만 대신에 각 값의 첫 번째 항목으로 그룹을 주문에 의해 그 그룹 값으로하지 자연적으로 일종의 않는, 모든 길이의 첫 번째 발생이 감소하는 순서로합니다. 고유성 필터링이 이것을 망칠 수는 없다고 100 % 확신하지 못하지만 아직 테스트 사례가 나오지 않았습니다.


1

05AB1E , 10 바이트

Œʒ¢}é.γg}н

빈 문자열에 대해서는 아무것도 출력하지 않습니다.

온라인으로 시도 하거나 모든 테스트 사례를 확인하십시오 .

설명:

Œ           # Get all substrings of the (implicit) input-String
 ʒ          # Filter it by:
  ¢         #  Count how many times the current substring occurs in the (implicit) input-String
            #  (only 1 is truthy in 05AB1E, so the filter will leave unique substrings)
          # After the filter: sort the remaining substrings by length
     g}   # Then group them by length as well
         н  # And only leave the first group containing the shortest substrings
            # (which is output implicitly as result)

이것은 05AB1E가 1진실한 가치 만을 가지고 있고 다른 모든 것은 거짓이라는 장점을 가지고 있습니다. 가장 짧은 고유 하위 문자열은 항상 가능한 모든 입력 문자열에 대해 정확히 한 번만 발생하도록 보장됩니다. (동일한 문자 (예 :) 만 포함 aaaaa하는 입력 문자열의 경우 하위 문자열과 같은 입력 문자열 자체는 한 번만 발생하므로 결과는 ["aaaaa"]입니다. 반복 패턴이있는 입력 문자열 (예 "abcabc":)의 경우 여전히 유일한 하위 문자열이 있음) 한 번만 발생하면 ( ["abca","abcab","abcabc","bca","bcab","bcabc","ca","cab","cabc"])이됩니다 ["ca"].)


0

파이썬 2, 150

import re
a=input()
r=range
l=len(a)
d=0
for i in r(l):
 if d:break
 for j in r(l-i):
  k=a[j:i+j+1]
  if len(re.findall("(?="+k+")",a))<2:d=1;print k

회색 영역은 인쇄해야 ""하지만 아무것도 인쇄하지 않습니다.
Jakube

1
@Jakube "출력의 정확한 형식은 유연합니다"
KSFT

그러나 당신은 전혀 출력이 없습니다.
Jakube

2
@Jakube 출력은 예상대로 빈 문자열입니다. 나는 그 주위에 따옴표가 없습니다.
KSFT

1
@Jakube 빈 문자열은 어쨌든 특별한 경우이므로 이것을 허용합니다.
Zgarb

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.