에 10 비트를 설정하기 위해 사용 일치하는 위치를 찾고 대체 할 기본 2 패스 알고리즘
10MB 파일의 경우 반 준 노트북에서 약 10 초가 소요됩니다. 더 빠르게 진행하기를 원한다면, 깔끔하고 강력하지는 않은 BitArray 추상화 대신에 바이트 배열과 마스크를 사용하여 구현할 수 있습니다.
안전하지 않은 코드를 사용하여 포인터를 사용하고 훨씬 빠른 복사를 할 수 있습니다 ...하지만 C# 질문이므로 이미 BitArray 추상화를 사용하고 있으므로 그것이 어떻게 달성 될 수 있는지.
private static BitArray Replace(BitArray input, BitArray pattern, BitArray replacement)
{
var replacementPositions = GetReplacementPositions(input, pattern);
return PerformReplacements(input, pattern.Length, replacement, replacementPositions);
}
private static List<int> GetReplacementPositions(BitArray input, BitArray pattern)
{
if (pattern.Length == 0) throw new Exception("Pattern cannot have 0 length");
var matchIndicies = new List<int>();
var maxCheckIndex = input.Length - pattern.Length;
var i = 0;
while (i <= maxCheckIndex)
{
if (MatchesAt(input, pattern, i))
{
matchIndicies.Add(i);
i += pattern.Length;
continue;
}
i++;
}
return matchIndicies;
}
private static bool MatchesAt(BitArray input, BitArray pattern, int index)
{
for (var j = 0; j < pattern.Length; j++)
{
if (input[index + j] != pattern[j]) return false;
}
return true;
}
private static BitArray PerformReplacements(BitArray input, int patternLength, BitArray replacement, List<int> replacementPositions)
{
var outLength = input.Length + replacementPositions.Count * (replacement.Length - patternLength);
var output = new BitArray(outLength);
var currentReadIndex = 0;
var currentWriteIndex = 0;
foreach (var matchPosition in replacementPositions)
{
var inputSubstringLength = matchPosition - currentReadIndex;
CopyFromTo(input, output, currentReadIndex, inputSubstringLength, currentWriteIndex);
currentReadIndex = matchPosition + patternLength;
currentWriteIndex += inputSubstringLength;
CopyFromTo(replacement, output, 0, replacement.Length, currentWriteIndex);
currentWriteIndex += replacement.Length;
}
CopyFromTo(input, output, currentReadIndex, input.Length - currentReadIndex, currentWriteIndex);
return output;
}
private static void CopyFromTo(BitArray from, BitArray to, int fromIndex, int fromLength, int toIndex)
{
for (var i = 0; i < fromLength; i++)
{
to.Set(toIndex + i, from.Get(fromIndex + i));
}
}
예를 들려 줄 수 있습니까? –
내가이 패턴을 가지고 있다고 가정 해 봅시다 : '010101'과'X'로 바꾸고 싶습니다. – Ben
이 패턴을 배열에 나타나는 모든 위치로 대체 하시겠습니까? –