와일드 카드 문자열이 세트의 다른 와일드 카드 문자열과 완전히 일치하는지 판별


9

잠시 동안 나를 괴롭힌 문제가 있습니다. 문자열 이 1과 0 의 시퀀스이고 와일드 카드 문자열 이 1, 0 및? s 의 시퀀스 라고 가정하겠습니다 . 모든 문자열과 와일드 카드 문자열의 길이는 같습니다. 이들은 표준 UNIX 와일드 카드입니다. 10 ?? 1은 10011, 10111 등과 일치합니다. 해당 위치에서 1 또는 0과 일치합니다. 경우 및 와일드 카드 문자열, 우리는 쓰기 w V \ 당량 일치 모든 문자열 경우 V가 도 일치한다 w를 .vwv≤wvw

문제 : 와일드 카드 문자열 세트 S 와 쿼리 v (와일드 카드 문자열)가 주어지면 v \ leq w ? 와 같은 w \ in S가 있습니까? 그렇지 않은 경우 v 를 S에 효율적으로 추가 할 수 있습니까?w∈Sv≤wvS

다음은 명백한 O(kmn) 솔루션입니다 (여기서 k 는 문자열의 크기, m 은 RAM의 단어 크기 (일반적으로 32 또는 64)) : 목록의 각 요소를 살펴보고 테스트하십시오. 조건 (비트 트위들 링을 사용하여 2 또는 3 작업에서 수행 할 수 있음). 또한 스캔하는 동안 v≥w 가 모든 항목 w 를 보유 하는지 테스트하십시오 . 경우 v 우리의 테스트에 실패하고 추가 v 세트에, 그리고 제거 w 우리가 표시들 '.

그러나 그것은 충분히 빠르지 않습니다. O(log⁡n) 솔루션이 있거나 완벽한 세계에서 기수 트리 ( O(k) ) 와 유사한 복잡성 이 있다면 정말 멋질 것입니다 . 쿼리가 대략 정확 하다는 것도 괜찮습니다 . 즉, v≤w 인 경우 yes 또는 no를 반환합니다. 그러나 조건이 확실하지 않으면 no를 반환하십시오.

이것이 최악의 경우에 도움이되지는 않지만 S의 모든 요소 S가 와일드 카드 문자열로 묶여 있다고 가정 할 수 있습니다 . 즉, 모든 w \ in S 에 대해 v \ geq w 와 같은 v 가 있습니다 .vw∈Sv≥w

내가 시도한 아이디어

  • 와일드 카드 문자열은 결합-실 밀화를 형성합니다. 와일드 카드 문자열을 포함하는 n-ary 트리를 가질 수 있습니다. 나뭇잎은 와일드 카드 문자열이되고 가지는 모든 어린이의 조인을 나타냅니다. 쿼리와 조인을 비교할 수없는 경우 해당 지점의 모든 자식과 비교하려고 시간을 낭비하지 않아도됩니다. 또한 업데이트를 수행하고 업데이트가 조인보다 큰 경우 전체 분기를 간단히 삭제할 수 있습니다. 불행히도, 이것은 최악의 경우 여전히 이며, 요소를 추가하기 위해 트리를 스캔 할 때 항상 "최상의"조인을 찾지는 않습니다.O(n)
  • 의 기수 트리를 형성 할 수 있습니다. 우리는 가 와일드 카드 문자열에 의해 묶여 있음을 알고 있습니다 . 그것이? 0? 0이라고 가정하십시오. 그런 다음 trie의 모든 분기는 문자열의 첫 번째 비트와 세 번째 비트에만 있어야합니다. 쿼리에서 분기하는 현재 비트가 1이면? 그리고 1 개의 가지; 0이면?를 확인합니다. 그리고 0 가지; 그것이?라면, 우리는? 분기. 우리는 잠재적으로 여러 개의 브랜치를 가져야하기 때문에 그리 좋아 보이지 않습니다 (같은 이유로 트라이를 업데이트하기는 어렵습니다). 매칭은 매우 빠른 작업이므로 트리에서 많은 순회를 수행하는 순진한 전략과 비교할 때 아프다 (포인터를 따르는 것이 일부 OR 및 AND를 수행하는 것보다 훨씬 비쌉니다).SS

관련된 일

  • 네트워킹 커뮤니티에서이 문제는 "패킷 분류"로 나타납니다. 여기에는 알려진 알고리즘 및 데이터 구조에 대한 훌륭한 조사가 있습니다 . 불행하게도, 와일드 카드 문자열은 접두사 만 일치한다고 가정하고 쿼리는 이러한 문자열의 튜플입니다. 물론 일반적인 와일드 카드 문자열을 다음 기준에 맞게 변환 할 수 있습니다. 1? 00? 1 ?? (1, β, 0, 0, β, 1, β, β)이다. 그러나 이것은 효율적이지 않습니다. 다른 가정은 이러한 튜플이 "색상"과 연관되어 있고 쿼리는 색상이 일치하는 것만이 아니라 색상을 반환해야한다는 것입니다. 이것은 튜플을 주문해야하기 때문에 (또는 (0,?) 및 (?, 1) 중 어느 것이 (0, 1)과 일치하는지 모호하기 때문에) 문제를 훨씬 더 어렵게 만듭니다.

  • 알고리즘 커뮤니티에서 "무관심"과 일치하는 하위 문자열을 찾는 것과 관련된 많은 결과를 발견했습니다. 이것은 상당히 어려운 문제이며 실제로 어떤 기법도 사용할 수 없습니다.

결론적으로

도움을 주셔서 감사합니다!


1
줄은 얼마나 클 수 있습니까? 그리고 왜 복잡성에서 그들의 길이를 설명하지 않습니까? 분명히 문자열은 이어야합니다. 그렇지 않으면 작업 할 고유 한 문자열 이 없습니다 . 또한 길이의 문자열 을 허용 하면 최악의 경우 데이터 구조의 모든 문자열을 봐야합니다 ... 문자열 길이에 경계가 있습니까? 폴리 로그? ? Ω(logn)nO(n)o(n)
— Artem Kaznatcheev

확실하지 않으면 죄송합니다. 문자열의 크기 는 입니다. 모든 의도와 목적을 위해 32 자 길이로 생각할 수 있습니다. "문자열"은 문제의 프레이밍을위한 편리한 추상화 일뿐입니다. 실제로는 (정수, 비트 마스크) 튜플로 표시되므로 몇 가지 기계 작업만으로 조인 및 를 계산할 수 있습니다 . (물론 정수 및 비트 마스크 필드의 수를 늘림으로써 문제는 더 큰 상수 크기 문자열로 자연스럽게 확장 될 수 있습니다). O(1)v≤w
— Christopher Monsanto

위의 의견은 아마도 복잡성 인수에 도움이되지 않을 것입니다 : (. 실제로 문자열의 크기를 다양하게 허용하는 경우 문자열의 크기와 집합의 크기 사이에는 아무런 관계가 없습니다. 것에 대해 사실 어쨌든 내가 훨씬 더 평균의 경우 관심 (또는 근사치) 오전, 불행한 최악의 경우지만.O(n)
— 크리스토퍼 몬산토

답변:


3

유한 상태 오토 마톤을 사용하는 것은 어떻습니까? 언어 는 유한하므로 규칙적입니다. 아래의 변환 후에도 여전히 규칙적입니다. 따라서 정규식을 결정적 유한 상태 오토 마톤으로 변환하는 일반적인 단계를 수행 한 후 시간 에 원하는 것을 인식 할 수 있습니다 . 아래 제안 된 내용에 버그가있는 경우이 아이디어가 여전히 작동하기를 바랍니다.SO(k)

주름은 와일드 카드 연산자를 처리하는 방법입니다. 와일드 카드 문자열의 와일드 카드는 테스트 문자열의 0 또는 1과 일치합니다. 그러나 와일드 카드 문자열을 인식하려고하므로 와일드 카드 문자열의 와일드 카드는 0, 1 또는? 다른 와일드 카드 문자열에서. 이 세트는 여전히 규칙적이므로 모든? 수직 막대가 일반적인 대체 연산자 인 정규식 (0 | 1 |?) 따라서 전체 집합 가 {10 ?? 1, 0? 1? 0}이면 정규 표현식은 (10 (0 | 1 |?) (0 | 1 |?) 1 | 0 (0 | 1 | ?) 1 (0 | 1 |?) 0)S

머신에 문자열을 추가하는 경우, 유한 상태 오토 마톤을 점차적으로 변경하는 작업이 있습니다. Daciuk 등 의이 논문 을 참조하십시오 : "최소 비 환식 유한 상태 오토마타의 증분 구성".

도움이 되나요?


나는 automata를 고려했습니다. 그렇습니다. 그러나 나는 오토마타를 점진적으로 구성하는 그런 작업을 찾지 못했습니다. 포인터 ShyPerson에게 감사드립니다.
— Christopher Monsanto

나는 Daciuk, et al 논문을 인용했다. 왜냐하면 그것이 달성하려는 것과 가장 비슷해 보였기 때문이다. 그러나 Carrasco와 Forcada의 논문 "최소 유한 유한 상태 자동 증분의 증분 구성 및 유지 관리"에서 finitepress state automata에 대한 문제가 최근에 더 많이 해결되었다고 언급 할 가치가 있다고 생각합니다. mitpressjournals.org/doi/abs/10.1162/ …
— ShyPerson

좋아, 나는이 주제에서 더 많은 것을 얻을 것이라고 생각하지 않으므로 귀하의 답변을 받아들입니다. 감사!
— Christopher Monsanto
당사 사이트를 사용함과 동시에 당사의 쿠키 정책과 개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.