C中的反转数组逻辑无法正常工作

时间:2021-12-14 21:28:25

I am trying to read the input to my program (a string of chars) and invert the order of the words that are in it.

我试图读取我的程序的输入(一串字符)并反转其中的单词的顺序。

For example, if I were to pass my program ABC DEF GHI JKL it would output JKL GHI DEF ABC. I am using the whitespace as separators.

例如,如果我通过我的程序ABC DEF GHI JKL,它将输出JKL GHI DEF ABC。我使用空格作为分隔符。

My code:

char toReverse[1000];
char outputArray[1000];
int charCount = //Size of the toReverse array. Varies on the input
                //It is the total number of chars stored in the array
...
int i;
int tempCharCount = charCount;
int wordSize = 0;
int outputIndex = 0;
int sentenceIndex = 0;
int charStep = 0;
for(i = charCount-1; i>=0; i--){
    if(toReverse[i] == ' '){
        int j;
        sentenceIndex = tempCharCount - wordSize;
        for(j = 0; j<charStep; j++){
            outputArray[outputIndex++] = toReverse[sentenceIndex++];
        }
        outputArray[outputIndex] = ' ';
        outputIndex++;
        charStep = 0;
    }
    wordSize++;
    charStep++;

}

There is a flaw in my code. I do know why this happens though. For example, if I were to pass as input ABC DEF GHI, it will only output GHI DEF. This is because whenever the outer for loop reaches index 0 of my toReverse array, since it is not a space ' ', it does not do the if(toReverse[i]) inner for(j = 0; j<charStep; j++) since the condition is not met.

我的代码存在缺陷。我知道为什么会这样。例如,如果我作为输入ABC DEF GHI传递,它将仅输出GHI DEF。这是因为每当外部for循环到达我的toReverse数组的索引0,因为它不是空格'',它不会为if(toReverse [i])内部执行(j = 0; j ;>

Do you have any advice regarding to the logic? I have tried reversing my logic, such as if(toReverse[i] != ' ') but it brings more problems than it solves.

你对逻辑有什么建议吗?我试过反转我的逻辑,比如if(toReverse [i]!='')但是它带来了比它解决的更多的问题。

Thanks for your advice and comments!

感谢您的建议和意见!

Cheers

Edit 1


I am reading my input from a file By the way!

我正在从文件中读取我的输入顺便说一下!

Update 1


Here I am basically trying to open various files and read chars from them

在这里,我基本上尝试打开各种文件并从中读取字符

int main(int argc, char * argv[])
{
    int i = 1;
    FILE * fp = NULL;

    if(1==argc){
    do_read(stdin);
    }else{
    // cycle through all files in command line arguments and read them
        for (i=1; i < argc; i++) {
            if ((fp = fopen(argv[i], "r")) == NULL) {
                printf("Failed to open file.\n");
            }
            else {
                do_read(fp);
                fclose(fp);

            }
        }
    }

    //printf("\n");

    //printf("\n");
    printf("%i",charCount);
    return 0;
}

3 个解决方案

#1


sample

#include <stdio.h>
#include <string.h>

void proc_rev(char toReverse[], char outputArray[]){
    int charCount = strlen(toReverse);
    int i;
    int tempCharCount = charCount;
    int wordSize = 0;
    int outputIndex = 0;
    int sentenceIndex = 0;
    int charStep = 0;
    for(i = charCount-1; i>=0; i--){
        if(toReverse[i] == ' '){
            int j;
            sentenceIndex = tempCharCount - wordSize;
            for(j = 0; j<charStep; j++){
                outputArray[outputIndex++] = toReverse[sentenceIndex++];
            }
            outputArray[outputIndex] = ' ';
            outputIndex++;
            charStep = 0;
        }
        wordSize++;
        charStep++;
    }
    outputArray[outputIndex] = '\0';
}

int main(void){
    FILE *fp = stdin;

    char toReverse[1000] = " ";
    char outputArray[1000];

    while(1 == fscanf(fp, "%998[^\n]%*c", &toReverse[1])){
        proc_rev(toReverse, outputArray);
        puts(outputArray);
    }

    return 0;
}

void do_read(FILE *fp){
    char toReverse[1000] = " ";
    char outputArray[1000];

    while(1 == fscanf(fp, "%998[^\n]%*c", &toReverse[1])){
        proc_rev(toReverse, outputArray);
        puts(outputArray);
    }
}

#2


This code is not tested but basic idea is reversing the whole string once and then reverse it word by word. idea is correct, implementation may have bugs

此代码未经过测试,但基本思路是将整个字符串反转一次,然后逐字反转。想法是正确的,实施可能有错误

void swap(char* s, int i, int j) {
    char tmp = s[i];
    s[i] = s[j];
    s[j] = tmp;
}


void rev(char* stirng, int start, int len) {
    for (int i=0; i<len/2; ++i) {
       swap(string, i, len-i-1);
    }
}

int main() {
    char* string = read from file
    int len = strlen(string);
    rev(string, 0, len);

    for (int i=0; i<len;) {
        int l = 0;
        int j=i;
        while (j<len && string[j]!=' ') ++j;
        rev(string, i, j-i);
        i=j+1;
    }
}

#3


The current logic reverses individual words from last to second word. However to reverse the first word you will have to add a check apart from if(toReverse[i] == ' ') as the first character need not be a space. A separate check can be used when counter 'i' reaches zero, i.e. first character

当前逻辑将单个单词从最后一个单词反转为第二个单词。但是要反转第一个单词,除了if(toReverse [i] =='')之外,你必须添加一个检查,因为第一个字符不必是空格。当计数器'i'达到零时,即第一个字符,可以使用单独的检查

#1


sample

#include <stdio.h>
#include <string.h>

void proc_rev(char toReverse[], char outputArray[]){
    int charCount = strlen(toReverse);
    int i;
    int tempCharCount = charCount;
    int wordSize = 0;
    int outputIndex = 0;
    int sentenceIndex = 0;
    int charStep = 0;
    for(i = charCount-1; i>=0; i--){
        if(toReverse[i] == ' '){
            int j;
            sentenceIndex = tempCharCount - wordSize;
            for(j = 0; j<charStep; j++){
                outputArray[outputIndex++] = toReverse[sentenceIndex++];
            }
            outputArray[outputIndex] = ' ';
            outputIndex++;
            charStep = 0;
        }
        wordSize++;
        charStep++;
    }
    outputArray[outputIndex] = '\0';
}

int main(void){
    FILE *fp = stdin;

    char toReverse[1000] = " ";
    char outputArray[1000];

    while(1 == fscanf(fp, "%998[^\n]%*c", &toReverse[1])){
        proc_rev(toReverse, outputArray);
        puts(outputArray);
    }

    return 0;
}

void do_read(FILE *fp){
    char toReverse[1000] = " ";
    char outputArray[1000];

    while(1 == fscanf(fp, "%998[^\n]%*c", &toReverse[1])){
        proc_rev(toReverse, outputArray);
        puts(outputArray);
    }
}

#2


This code is not tested but basic idea is reversing the whole string once and then reverse it word by word. idea is correct, implementation may have bugs

此代码未经过测试,但基本思路是将整个字符串反转一次,然后逐字反转。想法是正确的,实施可能有错误

void swap(char* s, int i, int j) {
    char tmp = s[i];
    s[i] = s[j];
    s[j] = tmp;
}


void rev(char* stirng, int start, int len) {
    for (int i=0; i<len/2; ++i) {
       swap(string, i, len-i-1);
    }
}

int main() {
    char* string = read from file
    int len = strlen(string);
    rev(string, 0, len);

    for (int i=0; i<len;) {
        int l = 0;
        int j=i;
        while (j<len && string[j]!=' ') ++j;
        rev(string, i, j-i);
        i=j+1;
    }
}

#3


The current logic reverses individual words from last to second word. However to reverse the first word you will have to add a check apart from if(toReverse[i] == ' ') as the first character need not be a space. A separate check can be used when counter 'i' reaches zero, i.e. first character

当前逻辑将单个单词从最后一个单词反转为第二个单词。但是要反转第一个单词,除了if(toReverse [i] =='')之外,你必须添加一个检查,因为第一个字符不必是空格。当计数器'i'达到零时,即第一个字符,可以使用单独的检查