我正在尝试读取ANSI格式的文件并将其转换为二进制文件。我正在声明两个动态内存分配:char* binary_reverse = new char;
和char * binary = new char;
调试时我看到这个(二进制)包含太多的垃圾值。为什么会这样?
我正在删除这些:delete binary_reverse;删除二进制; 但是,在删除期间它给我错误:
'ASCIItoBinary.exe':已加载'D:\ TryingBest \ Reactice \ ASCIItoBinary \ Debug \ ASCIItoBinary.exe',已加载符号。 'ASCIItoBinary.exe':加载'C:\ Windows \ SysWOW64 \ ntdll.dll',无法找到或打开PDB文件 'ASCIItoBinary.exe':加载'C:\ Windows \ SysWOW64 \ kernel32.dll',无法找到或打开PDB文件 'ASCIItoBinary.exe':加载'C:\ Windows \ SysWOW64 \ KernelBase.dll',无法找到或打开PDB文件 'ASCIItoBinary.exe':已加载'C:\ Windows \ SysWOW64 \ msvcr100d.dll',已加载符号。 HEAP [ASCIItoBinary.exe]:堆积在00241ED0修改为00241EFD,请求大小超过25 Windows已在ASCIItoBinary.exe中触发了断点。
以下是我在做代码的方式:
#include <cstring>
void AtoB(char * input)
{
unsigned int ascii; //used to store ASCII number of a character
unsigned int length = strlen(input);
//cout << " ";
for (int x = 0; x < length; x++) //repeat until the input is read
{
ascii = input[x];
char* binary_reverse = new char; //dynamic memory allocation
char * binary = new char;
//char binary[8];
int y = 0;
while (ascii != 1)
{
if (ascii % 2 == 0) //if ascii is divisible by 2
{
binary_reverse[y] = '0'; //then put a zero
}
else if (ascii % 2 == 1) //if it isnt divisible by 2
{
binary_reverse[y] = '1'; //then put a 1
}
ascii /= 2; //find the quotient of ascii / 2
y++; //add 1 to y for next loop
}
if (ascii == 1) //when ascii is 1, we have to add 1 to the beginning
{
binary_reverse[y] = '1';
y++;
}
if (y < 8) //add zeros to the end of string if not 8 characters (1 byte)
{
for (; y < 8; y++) //add until binary_reverse[7] (8th element)
{
binary_reverse[y] = '0';
}
}
for (int z = 0; z < 8; z++) //our array is reversed. put the numbers in the rigth order (last comes first)
{
binary[z] = binary_reverse[7 - z];
}
//printf("the Binary is %s",binary);
//cout << binary; //display the 8 digit binary number
delete binary_reverse; //free the memory created by dynamic mem. allocation
delete binary;
}
}
我想要“二进制”中的确切二进制值。不是二进制值和垃圾?如何消除垃圾值?如何避免堆损坏?
答案 0 :(得分:1)
问题是您只使用new char
命令分配了1个字符。您想使用new char[9]
分配更多内容。由于您打印的最多8位,因此null终结符需要一个额外的char。请务必在字符串末尾设置binary_reverse[y]=0
。
然后delete[]
代替delete
。
但是,您应该使用std::string
或std::vector
而不是......
答案 1 :(得分:1)
原来这里有一堆错误,几乎所有这些都是因为没有终止输出字符串,然后朝着错误的方向前进,寻找修复。
我将忽略
中的错误char* binary_reverse = new char;
除了说OP需要更多存储空间。
char* binary_reverse = new char[8];
正确的方法是返回它看起来像OP开始的临时分配,并添加一个额外的字节来包含字符串的空终止符。然后使用该空格作为空终止符。
没有null终结符,你就没有字符串。你有一个二进制blob。打印例程,所有c风格的字符串例程,依赖于那里的终结符。如果没有它,他们就不会知道弦的结束位置,然后进入寻找它的野生蓝色边缘。经常发生坏事。或者它可能没有。走出数组时会发生什么是未定义的。也许它做你想要的。也许它没有。没办法确定。在这种情况下,从轨道上获取网站甚至无法工作。
所以分配临时存储:
char binary_reverse[8]; // not using this one like a string so we don't need a terminator
char binary[9]; // printing this one. Need a terminator to know when to stop printing.
稍后,在构造binary_reverse
然后转移到binary
之后,需要终止binary
成为字符串而不仅仅是另一个匿名二进制blob。
binary[8] = '\0';
现在可以打印了。
建议:
Visual Studio有一个很棒的调试器。熟悉它。为你节省很多时间。
如果OP没有注释掉印刷品陈述的可能性很高,有人会在昨晚看到主要的错误。最小化代码是好的,但OP删除了bug的可见表现。
此代码可以大大简化。你知道你想要8位,因为你在ascii工作(嗯,实际上ascii是7位,但是除了8位之外几乎看不到任何东西)。将while (ascii != 1)
转换为for (int count = 0; count < 8; count++)
并测试角色中的所有8位。稍后再保存几个循环,因为现在你总是得到8位。