乱码字符串输出

时间:2015-10-14 06:33:53

标签: c arrays string stdio

我目前正在进行一项任务,要求我审查argv和输入重定向的单词。

我的问题在我的输出中很明显,可以在下面找到。我有很多跟踪打印声明,可能会或可能不会帮助您指出我的问题。

我的意图是:

  1. 获取file.txt
  2. file.txt的内容复制到buffer[x][y],其中[x]是一个字词串,[y][x]的字符。
  3. argv[]参数与buffer[][]进行比较。
  4. 创建newstr[size2]。对于argv[]中找到的每个buffer[][]争论,请将其替换为replace[9] = "CENSORED"
  5. 打印newstr[0 to (size2-1)]
  6. 字符串

    这是我的代码:

    // censored.c
    #include <stdio.h>
    #include <string.h>
    #include <stdlib.h>
    #include <ctype.h>
    #define SIZE 128
    
    int main ( int argc, char* argv[])
    {
        int i = 0;
        int j = 0;
        int k = 0;
        char buffer[SIZE][SIZE];
        char x;
        int count = 0;
        int size1 = sizeof(buffer);
        int size2 = 0;
        char replace[9] = "CENSORED";
        int buffersize=0;
        printf("tracing: size1: %d.\n", size1);
        printf("tracing: argc: %d.\n", argc);
        while((fscanf(stdin, "%c", &x)!=EOF))
        {
            if(isalpha(x))
            {
                buffer[i][j]=x;
                printf("tracing: buffer[%d][%d]: %c\n", i,j, buffer[i][j]);
                j++;
            }
            else if(isspace(x)) // if whitespace
            {
                j = 0;
                i++;
                buffer[i][j]=x;//this should be buffer[i][j]
                printf("tracing: buffer[%d][%d]: %c\n", i,j, buffer[i][j]);
                j = 0;
                i++;
            }
            else if(ispunct(x)) // if x is a punctuation
            {
                j = 0;
                i++;
                buffer[i][j]=x;//this should be buffer[i][j]
                printf("tracing: buffer[%d][%d]: %c\n", i,j, buffer[i][j]);
            }
            else if(iscntrl(x)) // if control key (\n, \r etc...)
            {
                j = 0;
                i++;
                buffer[i][j]=x;//this should be buffer[i][j]
                printf("tracing: buffer[%d][%d]: %c", i,j, buffer[i][j]);
                j = 0;
                i++;
            }
            else if(isdigit(x))
            {
                buffer[i][j]=x;//this should be buffer[i][j]
                printf("tracing: buffer[%d][%d]: %c\n", i,j, buffer[i][j]);
                j++;
            }
            else
            {
                break;
            }
        }
        size2 = i;
        printf("tracing: buffer[8][0]:%s\n",buffer[8]);
        char newstr[size2][SIZE];
        i = 0;
        j = 0;
    //  tracing:
        printf("tracing: line 72\n");
        printf("tracing: size2: %d.\n", size2);
        while(i < size2) //print buffer[]
        {
            printf("%s", buffer[i]);
            i++;
        }
    
        printf("tracing: line 80\n");
        for(k=1; k < argc; k++)
        {
            printf("%s\n", argv[k]);
        }
    //  end tracing
        i = 0; //reinitialize i
        j = 0; //reinitialize j
    //  creating newstr[SIZE] and censoring words
        printf("tracing: line 89\n");
        for(i = 0; i < size2; i++)
        {
            for(j=1; j < argc; j++)
            {
                if(strcmp(buffer[i], argv[j])==0)
                {
                    strcpy(newstr[i], &replace[0]);
                    printf("tracing: replaced at [%d]\n", i);
                    break;
                }
                else
                {
                    strcpy(newstr[i], buffer[i]);
                    printf("tracing: copied at [%d]\n", i);
                }
            }
        }
        i = 0; //reinitialize i
        while(i < size2)
        {
            printf("%s", newstr[i]);
            i++;
        }
        return 0;
    }
    

    假设我输入了名为file.txt的重定向文件及其内容:

    Said Hamlet to Ophelia,
    I'll draw a sketch of thee,
    What kind of pencil shall I use?
    2B or not 2B?
    

    我的意见是:

    ./censored Ophelia thee 2B < file.txt
    

    这是我得到的奇怪输出:

    Said Hamlet to CENSORED, Ill draw a sketch ???)ofoQ? ?"h?CENSORED,2oQ?
    What? /oQ?kind? of 6oQ?pencil +oQ?shall ?"h?I-oQ? ???)use? ???2BoQ?
    7oQoroQ Qnot 1oQ?CENSORED?4oQ?
    

    感谢任何帮助,我知道我的代码很乱,这是我第一次学习学习C.

1 个答案:

答案 0 :(得分:2)

我有好消息和坏消息,坏消息是:我发现了一些错误和错误。 好的一点是:所有这些对初学者来说都很常见!

第一个:buffer[]中的字符串不以'\0'终止,而newstr是字符串指示符的结尾。这是导致问题的原因之一。 以下是其他的:

  • char buffer [SIZE] [SIZE]; 在这里,您正在考虑单词的数量和单词的长度不能超过128,这将导致分段错误,只要此条件错误。我建议你学习动态分配(malloc())。
  • for(j = 1; j&lt; argc; j ++)如果argc == 1,则不会进入此循环,这会导致main()为空。通常我们使用NULL指针结束数组,然后在读取数组时检查数组的每个字符串是否为非null,以便我们不会尝试使用未定义的内容。
  • 正如您所指出的,您的代码非常混乱,下次尝试在函数中分离您的代码而不是j = 0; i++; buffer[i][j]=x;//this should be buffer[i][j] printf("tracing: buffer[%d][%d]: %c\n", i,j, buffer[i][j]); j = 0; i++;中的代码。
  • 尝试减少这种情况,写入的行数越少,代码的读取和调试就越容易:

public class EventsFragment extends android.support.v4.app.Fragment { private StackView stackView; private ArrayList<Stack_Items> list; TypedArray eventLogo; String eventName[],eventDesc[]; @Nullable public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { eventLogo = getResources().obtainTypedArray(R.array.event_stack_icon); eventName = getResources().getStringArray(R.array.event_stack); eventDesc = getResources().getStringArray(R.array.event_desc_stack); View view = inflater.inflate(R.layout.events_layout, null); stackView = (StackView) view.findViewById(R.id.stackView1); list = new ArrayList<Stack_Items>(); //Adding items to the list for (int i = 0; i < eventLogo.length(); i++) { list.add(new Stack_Items(eventName[i], eventLogo.getResourceId(i, -1))); } //Calling adapter and setting it over stackView Stack_Adapter adapter = new Stack_Adapter(getActivity().getApplicationContext(), list); stackView.setAdapter(adapter); stackView.setOnItemClickListener(new AdapterView.OnItemClickListener() { public void onItemClick(AdapterView<?> a, View view, int position, long id) { MainActivity mainActivity = (MainActivity) getActivity(); FragmentTransaction fragmentTransaction = mainActivity.getSupportFragmentManager().beginTransaction(); Fragment eventDescFragment = new DynamicEventsPage().newInstance(R.array.event_stack,R.array.event_desc_stack,eventLogo.getResourceId(position, -1)); fragmentTransaction.replace(R.id.containerView, eventDescFragment); fragmentTransaction.commit(); } }); adapter.notifyDataSetChanged(); return view; } }

  • 这个建议与那种旨在阅读大量数据的程序并不相关,但请记住:尽量避免存储数据。

我认为现在已经足够了,祝你好运,为我可怜的英语道歉。