我正在撰寫一個將十進制數轉換為羅馬數的程式。我使用 4 個陣列thousands, hundreds, tens,units將數字存盤在羅馬數字中,然后將每個數字復制到res陣列中,我使用str指標來跟蹤字串的res開始位置。當我使用輸入進行測驗時128,它會列印出CXXVIIIIX必須是CXXVIII. 我嘗試除錯并在tmp=8is時得到結果strlen(units[tmp-1]) = 6,這意味著strlen也很重要IX。對于某些情況,例如3888,程式會列印出垃圾值。
這是我的代碼
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <stdbool.h>
#include <string.h>
#include <windows.h>
int main(){
int n=128;
char thousands[][4]={"M","MM","MMM"};
char hundreds[][5]={"C","CC","CCC","CD", "D", "DC", "DCC", "DCCC", "CM"};
char tens[][5]={"X", "XX", "XXX", "XL", "L", "LX", "LXX", "LXXX", "XC"};
char units[][5]={"I", "II", "III", "IV", "V", "VI", "VII", "VIII", "IX"};
char res[16];
res[15]='\0'; //add nul to the last character of res array
char *str=res 14; //str tracks where the string start
int tmp;
//store roman digits in res array in reverse order,
//start from units->tens->hundreds->thousands
if (n!=0)
{
tmp=n%10;
if (tmp!=0)
{
str-=strlen(units[tmp-1]); //str steps back several address to store new digits
strncpy(str, units[tmp-1], strlen(units[tmp-1])); //use strncpy to copy without '\0'
}
n/=10;
}
if (n!=0)
{
tmp=n%10;
if (tmp!=0)
{
str-=strlen(tens[tmp-1]);
strncpy(str, tens[tmp-1], strlen(tens[tmp-1]));
}
n/=10;
}
if (n!=0)
{
tmp=n%10;
if (tmp!=0)
{
str-=strlen(hundreds[tmp-1]);
strncpy(str, hundreds[tmp-1], strlen(hundreds[tmp-1]));
}
n/=10;
}
if (n!=0)
{
tmp=n%10;
if (tmp!=0)
{
str-=strlen(thousands[tmp-1]);
strncpy(str, thousands[tmp-1], strlen(thousands[tmp-1]));
}
n/=10;
}
printf("%s", str);
return 0;
}
那么為什么會發生這種情況以及如何解決呢?
任何幫助,將不勝感激。
uj5u.com熱心網友回復:
修復所有字串文字的陣列大小后,會出現非一錯誤和未初始化的 char 陣列元素。
char res[16];"MMMDCCCLXXXVIII"有尾隨就足夠了'\0'。- 隨著
res[15]='\0';您將字串終止存盤在最后一個元素中。 char *str=res 14;在此之前設定指向未初始化字符的指標。str-=strlen(something)根據要插入的字串的長度移動指標。以下strncpy不會覆寫未初始化的字符。
結果將始終包含一個未初始化的尾隨字符,該字符可能可見也可能不可見。
"MMMDCCCLXXXVIII"由于尾隨未初始化字符,最大長度 ( ) 的結果將在第一個陣列元素之前開始一個字符。您將INH其實有一個結果字串"MMMDCCCLXXXVIII*",其中*被初始化。
例子:
int n=3888;
char res[16];
// * indicates an uninitialized character
res[15]='\0'; // "***************\0"
char *str=res 14; // str = &res[14]
int tmp;
tmp=n%10; // tmp = 8
str-=strlen(units[tmp-1]); // "VIII" (strlen = 4) -> str = &res[10]
strncpy(str, units[tmp-1], strlen(units[tmp-1])); // "**********VIII*\0"
n/=10; // n = 388
tmp=n%10; // tmp = 8
str-=strlen(tens[tmp-1]); // "LXXX" (strlen = 4) -> str = &res[6]
strncpy(str, tens[tmp-1], strlen(tens[tmp-1])); // ******LXXXVIII*\0"
n/=10; // n = 38
/* ...*/
// final result would be
// str = &res[-1]
// str -> "MMMDCCCLXXXVIII*\0"
// res = "MMDCCCLXXXVIII*\0"
// The last strncpy tries to write a character 'M' one element before the beginning of the array res.
作為修復我建議
char res[16] = {0}; // initialize the whole array with 0
char *str=res (sizeof(res)-1);
轉載請註明出處,本文鏈接:https://www.uj5u.com/caozuo/407462.html
標籤:
