为什么这段代码没有完成它的工作?
我想创建一个程序来写入文件中的所有素数(我知道有一个流行的算法“Eratosthenes筛”,但我试图自己做)。我试图消除仍然具有值1的字节的所有复杂性,然后将它们写入文件中。为什么这段代码没有完成它的工作?
#include <iostream>
#include <stdlib.h>
#include <stdio.h>
void afficher_sur_un_ficher (FILE* ficher, int nb_bit);
char el_mask (int x);
int main()
{
FILE* p_fich;
char tab[4096], mask, eli_mask;
int nb_bit = 0, x, f;
for (int i = 0; i < 4096; i++)
{
tab[i] = 0xff;
}
for (int i = 0; i < 4096; i++)
{
for (mask = 0x01; mask != 0; mask <<= 1)
{
if ((tab[i] & mask) != 0)
{
x = nb_bit;
while ((x > 1) && (x < 16384))
{
eli_mask = el_mask (x);
f = x/8;
tab[f] = tab[f]^eli_mask;
x = x + nb_bit;
}
afficher_sur_un_ficher (p_fich, nb_bit);
}
nb_bit++;
}
}
system ("PAUSE");
return 0;
}
void afficher_sur_un_ficher (FILE* ficher, int nb_bit)
{
ficher = fopen ("res.txt", "a+");
fprintf (ficher, "%d \t", nb_bit);
int static z;
z = z + 1;
if (z % 10 == 0)
fprintf (ficher, "\n");
fclose (ficher);
}
char el_mask (int x)
{
x = x % 8;
switch (x)
{
case 0:
x = 0b00000001;
break;
case 1:
x = 0b00000010;
break;
case 2:
x = 0b00000100;
break;
case 3:
x = 0b00001000;
break;
case 4:
x = 0b00010000;
break;
case 5 :
x = 0b00100000;
break;
case 6 :
x = 0b01000000;
break;
case 7:
x = 0b10000000;
break;
}
return x;
}
有似乎是在回路中的问题正试图清除位表明非素数:
while ((x > 1)&&(x < 16384))
{
tab[i] = tab[i]^mask ;
x = x * 2 ;
}
由于i
在这个循环不会改变,你基本上是切换同位关闭同时递增x
。除了将索引固定到tab[]
之外,您可能还希望将操作从异或(^
)更改为无条件清除该位的操作 - 一旦清除了一位,您不希望再次处理该位以获取不同的因子'重置'位。请注意,i
的简单递增将不会执行,因为其他tab
元素中的x
的倍数可能不在相同的位偏移量中(实际上,tab[]
的单个元素可能包含x
的几个倍数)。
即使你解决了这个问题,我认为循环可能没有达到你期望的水平,因为x = x * 2;
并不通过它的倍数走x
--你最终会跳过一些非质数。
一些关于'Eratosthenes筛'如何工作可能会有所帮助的研究。
谢谢,我解决了这个问题,但它仍然没有做正确的工作,并且它的'Sierat of eratosthenes',但我试图通过使用位来获得更多的素数:如果你想象每一位都是数组中的数字,你会得到[4096 * 8]中的所有素数,我将编辑我的问题,并尝试使其更清楚谢谢 – hamza 2010-04-17 19:50:57
也许我的“M失去了一些东西,但是这只是似乎靠不住的。我不记得了手共同的主要算法,但是,例如,
(excerpts) tab[i] = 0xff ; mask = 0x01 ;
for (int j = 0 ; j < 8 ; j++) { if ((tab[i] & mask) != 0) mask = mask<<1 ;
这意味着你将永远走8倍 - 那么,为什么用 '&' 检查
再一个,
x = nb_bit ; while ((x > 1)&&(x < 16384)) { tab[i] = tab[i]^mask ; x = x * 2 ; }
这只是在每次迭代时触发位。那是你要的吗?
最后,因为我不知道你的意思是要做什么,所以要小心你的对象的位长。你可能会触发器
0000 0000 1111 1111 0000^0001
或
1111 1111 1111 1111 0000^00001
正如我真的不明白你想要做什么,不知道这可能是相关的。
编辑(哈姆扎评论后):
是的。这是什么循环就如下 - 比较/ '和'
与
0000 0001
0000 0010
0000 0100,
,并始终将成立。我不知道你想在这里做什么,但这似乎很腥(改变位置现在没有互联网一段时间,但gl。:))。
谢谢,我只是编辑我的问题你可能想再读一遍现在再次感谢 – hamza 2010-04-14 00:34:46
您可以简化您的主要功能是几分:
int main (int argc, char** argv) {
FILE* p_fich;
char tab[4096] , mask;
int nb_bit = 0 , x;
memset(tab, 0xFF, 4096);
for (int i = 0; i < 4096; i++) {
for (mask = 0x01; mask != 0; mask <<= 1) {
if ((tab[i] & mask) != 0) {
for (x = nb_bit; (x > 1) && (x < 0x4000), x<<=1)
tab[i] ^= mask;
afficher_sur_un_ficher (p_fich, nb_bit);
}
nb_bit++;
}
}
system ("PAUSE");
return 0;
}
现在,为了解决你的问题: 你afficher_sur_un_ficher
功能将打印不管你传递给它,并调用该函数的每次循环,其中((tab[i] & mask) != 0)
是真的。由于您将每个tab[i]
字节初始化为0xFF
,因此屏蔽掉任何给定的位组合将始终导致if
语句评估true
。您正在更改tab[i]
的值,但一旦您这样做了,就不再使用该位,因此它不会改变总是采用if
语句的事实。这就是为什么你看到每个记录被记录。
编辑: 如果你简化了所有不影响决定输出或值来输出的代码,你结束了以下内容:
memset(tab, 0xFF, 4096);
for (int i = 0; i < 4096; i++) {
for (mask = 0x01; mask != 0; mask <<= 1) {
afficher_sur_un_ficher (p_fich, nb_bit);
nb_bit++;
}
}
正如你所看到的,这代码将打印一个递增的整数序列(0到(4096 * 8)-1),并且完全独立于tab
阵列以及i
和mask
的特定值。我认为在你的算法实现中缺少一些东西。你有链接到你想要实现的算法的描述?或者这是你开发的算法? (对不起,我不明白你对算法的描述,你添加到这个问题中)
感谢男人,所有我写的是写的在法国,但我会寻找的东西(对不起,我coudlnt连接的最后几天) 再次感谢 – hamza 2010-04-17 19:46:20
我想你会很难将所有的素数加到一个文件中......除非你有一个无限的时间量和无限的空间:) – 2010-04-14 00:09:25
也许他已经罢工了? – 2010-04-14 00:11:31
@布莱恩我假设他这样做是有限的在某些数字之间? – 2010-04-14 00:11:35