찾기 X-뒤집어 문자열는
예를 들면 고려 N = 10 인 경우, X = 4, 초기 문자열 :
flipped: 0000111111
4 때문에 비트가 다르다 :
initial: 0011010111
후 이것이 X-대칭 문자열의 예가 될 것이다. 당신이 두 개의 문자열을 XOR하면 얻을 다음 XOR-ED 문자열에서 4 세트 비트 (들)이 반전 된 4 비트의 위치를 나타냅니다
initial: 0011010111
flipped: 0000111111
XOR-ed: 0011101000
.
이제 이것을 거꾸로 생각해보십시오. 당신이 초기 문자열, 4 세트 비트 문자열을 가지고 있다면, 당신은에 의해 X-뒤집어 문자열을 생성 할 수 있습니다를 XOR을 - 보내고 :
initial: 0011010111
4 bits : 0011101000
XOR-ed: 0000111111
을 그래서 당신은 X 세트 길이 N의 모든 바이너리 문자열을 생성하는 경우 비트, 그리고 당신은 원래 문자열로 XOR, 당신은 모든 X 플립 문자열을 얻을.
initial 4 bits XOR-ed
0011010111 0000001111 0011011000
0000010111 0011000000
0000100111 0011110000
...
1110010000 1101000111
1110100000 1101110111
1111000000 1100010111
예를 들어, X 세트 비트를 사용하여 모든 N 길이 문자열을 생성 할 수 있습니다. Gosper's Hack. 아래의 코드 예제에서는 역순 사전 순서 함수를 사용합니다.이 함수는 원래 this answer으로 작성했습니다.
두 번 틀지
비트가 두 번 뒤집어 될 수 있다면, 하나의 비트 때문에, X가없는 X-뒤집어 문자열이 초기 문자열에서 다른,하지만 X-2 비트 가능성이 있습니다 뒤집어 원래 상태로 되돌 렸습니다. 또는 X-4, 비트가 4 번 뒤집 혔거나 두 개의 다른 비트가 두 번 뒤집 으면. 사실, 다른 비트의 수는 X, X-2, X-4, X-6 ... 1 또는 0 (X가 홀수인지 짝수인지에 따라 다름) 일 수 있습니다.
따라서 X 플립 된 모든 문자열을 생성하려면 X 플립 된 비트가있는 모든 문자열을 생성 한 다음 X-2 플립 된 비트가있는 모든 문자열을 생성 한 다음 X-4, X-6 ...을 1 또는 0으로 만듭니다.X는 N보다 큰 경우에는 X> N은
다음 명백히 몇몇 비트들은 한 번 이상 대칭 될 경우
. X에서 시작하여 X-2, X-4, X-6까지 카운트 다운하지만 ≤ N 값의 문자열 만 생성합니다. 따라서 실제적으로 N 또는 N- XN이 짝수 또는 홀수인지 여부에 따라 1입니다. 문자열
X와 N 길이 문자열의 개수
전체 수의 비트를 반전시켜 Binomial CoefficientN choose X
인 X 세트 비트를 가진 N 길이 스트링의 개수와 동일. 물론 X-2, X-4, X-6 ... 문자열을 고려해야합니다. 따라서 합계는 다음과 같습니다.
(N을 선택 X) + (N은 X를 선택하십시오. (X 또는 N을 선택하십시오)
X가 N보다 큰 경우 XN이 짝수 또는 홀수인지 여부에 따라 N choose N
또는 N choose N-1
에서 시작하십시오. N = 3 X = 2와 함께 예를 들어
총 개수이다
(10 choose 4) + (10 choose 2) + (10 choose 0) = 210 + 45 + 1 = 256
: N = 10, X = 4, 총 수는 위에서 예를 들면 (3 choose 2) + (3 choose 0) = 3 + 1 = 4
N = 6 다른 답변의 예
하고 정확한 개수 = 4 인 X :
(6 choose 4) + (6 choose 2) + (6 choose 0) = 15 + 15 + 1 = 31
예제 코드
이 JavaScript 코드 조각은 역 사전 식 순서로 (설정 비트가 왼쪽에서 오른쪽으로 이동하도록) 이진 문자열의 시퀀스를 생성 한 다음 위에서 설명한 예제의 결과 반전 문자열과 총 개수를 인쇄합니다 : X에 의해
function flipBits(init, x) {
var n = init.length, bits = [], count = 0;
if (x > n) x = n - (x - n) % 2; // reduce x if it is greater than n
for (; x >= 0; x -= 2) { // x, x-2, x-4, ... down to 1 or 0
for (var i = 0; i < n; i++) bits[i] = i < x ? 1 : 0; // x ones, then zeros
do {++count;
var flip = XOR(init, bits);
document.write(init + " ⊕ " + bits + " → " + flip + "<br>");
} while (revLexi(bits));
}
return count;
function XOR(a, b) { // XOR's two binary arrays (because JavaScript)
var c = [];
for (var i = 0; i < a.length; i++) c[i] = a[i]^b[i];
return c;
}
function revLexi(seq) { // next string in reverse lexicographical order
var max = true, pos = seq.length, set = 1;
while (pos-- && (max || !seq[pos])) if (seq[pos]) ++set; else max = false;
if (pos < 0) return false;
seq[pos] = 0;
while (++pos < seq.length) seq[pos] = set-- > 0 ? 1 : 0;
return true;
}
}
document.write(flipBits([1,1,1], 2) + "<br>");
document.write(flipBits([0,0,1,1,0,1,0,1,1,1], 4) + "<br>");
document.write(flipBits([1,1,1,1,1,1], 4) + "<br>");
당신이 문자열의 각 문자를 전환 할 수 있다는 것을 의미 화나게? – eol
한 플립에서 예, 문자가 0에서 1로 또는 그 반대로 변경됩니다. –
예!를 추가했습니다. –