Подскаите алгоритм
Apr. 15th, 2008 12:45 pmПодскажите что почитать чтобы разработать алгоритм для решения следующей задачи:
есть исходное двоичное число определенной размерности
есть массив с числами той же размерности
найти последовательность применения операции исходное_число=исходное_число XOR число из массива
чтобы в результате получилось ноль.
есть исходное двоичное число определенной размерности
есть массив с числами той же размерности
найти последовательность применения операции исходное_число=исходное_число XOR число из массива
чтобы в результате получилось ноль.
no subject
Date: 2008-04-15 09:11 am (UTC)no subject
Date: 2008-04-15 09:13 am (UTC)массив 36 элементов
no subject
Date: 2008-04-15 09:38 am (UTC)Задача чисто абстрактна или имеет конкретное практическое применение?
no subject
Date: 2008-04-15 09:39 am (UTC)no subject
Date: 2008-04-15 10:12 am (UTC)no subject
Date: 2008-04-15 10:34 am (UTC)что сначала
x= x xor m[1]
x= x xor m[3]
x= x xor m[2]
x= x xor m[1]
и так далее...
no subject
Date: 2008-04-15 10:44 am (UTC)Это во первых.
Во вторых счас попробую че-нить написать. Секунду.
no subject
Date: 2008-04-15 10:55 am (UTC)не скажу, как там задать long long int)
Тут сразу надо сделать
for( index = 0; index < 32; index++ )
nums[index] = nums[index] ^ исходное_число;
Функция вычисляет xor между исходными числами.
Числа выбираются как соответствующие биты
DWORD CalcXored( DWORD bits )
{
DWORD r = 0, index;
for( index = 0; index < 32; index++, bits = bits >> 1 )
if (bits & 1)
{
r = r ^ nums[index];
}
return r;
}
struct tagNum // структура для кеширования
{
DWORD xored_num;
DWORD index
};
Сначала взять первые 16 чисел (к примеру) и рассчитать TNums XoredNums[2 << 16] массив (размера 2^16 соответственно) вида
Сначала:
for( index = 0; index < (2 << 16); index++ )
{
Nums[index].index = index;
Nums[index].xored_num = CalcXor( DWORD bits )
}
Отсорировать массив по xored_num
Теперь берем остальные числа
for( index = 0; index < (2 << 16); index++ )
// тут уже надо не 2 << 16, а 2 << 20 ( тк 36-16=20 )
{
t = CalcXor( index << 16 );
Потом бинарный поиск в массиве XoredNums по полю xored_num.
Если нашли - результат найден. Числа, которые надо взять будут числа
(index << 16) | nums[ найденное ].index;
Если нет - продолдаем цикл.
}
Займет это всего О(16) + О(20) * ln( 2^16 ) циклов.
То есть О(20). Вот так вот примерно.
no subject
Date: 2008-04-15 10:57 am (UTC)В общем будет 2^16 + 2^20 * O(16) итераций.
no subject
Date: 2008-04-15 11:09 am (UTC)no subject
Date: 2008-04-15 11:18 am (UTC)no subject
Date: 2008-04-15 11:25 am (UTC)Помогло?
no subject
Date: 2008-04-15 11:51 am (UTC)то есть последовательность не важна, важно лишь какие числа брать...
таким образом количество проверок при переборе = 2^36, что не очень-то и много...
no subject
Date: 2008-04-15 12:01 pm (UTC)no subject
Date: 2008-04-15 10:56 am (UTC)A0*x0 ⊕ A1*x1 ⊕ ... ⊕ An*xn = C
Где Ai — числа из массива, C — исходное число, xi принимают значения 1 или 0, ⊕ — операция XOR. Предполагаю, что копать нужно в сторону решения линейных уравнений и дискретной математики.
no subject
Date: 2008-04-15 11:09 am (UTC)