文件输入和输出,循环创建新行

时间:2013-11-24 16:02:01

标签: c encryption file-io

我的代码出现问题。我有for循环,根据用户输入的密钥解密/加密短语。通过执行以下命令从命令行运行程序:

./program [-d] [-e] key sourcefile destinationfile

[-d]和[-e]表示解密或加密,用户只能指定一个选项。程序从源文件中获取文本短语,对其进行操作,然后将新短语写入新文件。但是,我注意到由于某种原因,我的for循环拆分了短语并根据密钥搞砸了新文件中的序列。当我加密时,看到我得到的结果:

key    source                      dest
2      Testing1234567890ABCDEF     Tsig24680BDFetn13579ACE      correct
3      Testing1234567890ABCDEF     Ttg369BEei1470CFsn258AD      correct
4      Testing1234567890ABCDEF     Ti260Den37AEsg47BFt159C      correct
5      Testing1234567890ABCDEF     Tn49Deg50Es16AFt27B          incorrect
                                   i38C
6      Testing1234567890ABCDEF     Tg6Be17Cs28Dt39Ei40Fn5A      correct
7      Testing1234567890ABCDEF     T18Ee29Fs30                  incorrect
                                   t4Ai5Bn6Cg7D
8      Testing1234567890ABCDEF     T20e3As4Bt5Ci6Dn7Eg8F19       correct
9      Testing1234567890ABCDEF     T3be4Cs5Dt6Ei7Fn8
                                   g9102A                       incorrect
10     Testing1234567890ABCDEF     T4De5Es6Ft7
                                   i8n9g01A2B3C                 incorrect

注意使用5,7,9和10如何将短语分成两行?那不应该发生,我甚至在循环中都没有换行符。我无法弄清楚是什么导致了这一点。

我的代码如下:

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

#define BUFFER_SIZE 100

int main ( int argc, char* argv[ ] ) {
        FILE* sourcefile;
        FILE* destfile;
        int i, j, filesize, key;
        int pos = 0;
        char phrase[ BUFFER_SIZE ];
        char* newPhrase;

        /* if user types -d or -e continue */
        if ( ( argc == 5 && ( strcmp ( argv[ 1 ], "-d") == 0 ) ) || ( argc == 5 && ( strcmp ( argv[ 1 ], "-d") == 0 ) ) ) {

                /* exit if key is not an int */
                key = atoi ( argv[ 2 ] );
                if ( key < 1 ) {
                        perror ( "Error: key is not a valid int" );
                        exit ( EXIT_FAILURE );
                }

                /* open source & destination files */
                sourcefile = fopen ( argv[ 3 ], "r" );
                /* display error message if source file does not exist */
                if ( sourcefile == NULL ) {
                        perror ( "" );
                        exit ( EXIT_FAILURE );
                }
                destfile = fopen ( argv[ 4 ], "w" );

                /* extract the text in the source file */
                fgets ( phrase, BUFFER_SIZE, sourcefile );
                fseek ( sourcefile, 0, SEEK_END );
                filesize = ftell ( sourcefile );

                /* allocate memory for new string that will go in destination file */
                newPhrase = ( char* ) malloc ( filesize );

                /* decrypt */
                if ( strcmp ( argv[ 1 ], "-d" ) == 0 ) {
                        for (i = 0; i < key; i++) {
                                for (j = i; j < strlen( phrase ); j += key)
                                        newPhrase[ j ] = phrase[ pos++ ];
                        }
                }
                /* encrypt */
                else {
                        for (i = 0; i < key; i++) {
                                for (j = i; j < strlen( phrase ); j += key)
                                        newPhrase[ pos++ ] = phrase[ j ];
                        }
                }
                /* write new phrase to file, close files */
                fputs( newPhrase, destfile );
                fclose ( sourcefile );
                fclose ( destfile );
        }
        return 0;
}

1 个答案:

答案 0 :(得分:2)

你的程序运行正常。

让您感到困惑的是,输入文件第一行末尾的尾随换行符包含在短语中。

因为短语(包括尾随换行符)是24个字符,并且您使用的是选择“第n个”字符的“加密”,当您有一个“n”分隔24时,事情会正常工作,因为尾部换行符最后是阶段结束。所以2,3,4,6和8都可以正常工作(你选择一个长度超过这么多除数的相位很有趣......)

但对于“n”的其他值,终止输入字符串的尾随换行符最终位于加密字符串的中间。一旦你看到,“不正确”的输出是正确的。

[编辑:]这已经更新;最初我认为它是0终止C中导致问题的字符串。原来的回答是错的,抱歉。

如果你想“修复”这个,你可以在阅读之后缩短字符串:

while (strlen(phrase) && phrase[strlen(phrase)-1] == '\n') phrase[strlen(phrase)-1] = '\0'

ps查看您的历史记录,您没有将答案标记为正确。通常情况下,如果有人发布了正确的答案,您点击答案上方和左侧的“勾号”标记,然后回答者(我)获得互联网积分,这对我们悲伤的生活有意义。