单线程实现检索当当网泄露的1GB用户数据


  1. 新建项目dangdangusersearch

2.编写头文件head.h

#ifndef _HEAD_H_

#define _HEAD_H_

 

#include <stdio.h>    //注意文件操作相关函数的头文件是stdio.h

#include<stdlib.h>    //为了使用system函数

#include <string.h>   //字符串操作所用到的头文件

#include<Windows.h>   //使用休眠函数时用到的头文件

#include <crtdbg.h>   //做内存泄露检測所需的头文件

 

//开启内存检測

#define _CRTDBG_MAP_ALLOC

 

/*菜单查看*/

extern void main_view();

 

/*获得文件的字节大小*/

extern int getFileSize(const char *path);

/*载入文件,fPath为传递进去的文件路径*/

extern void loadFile(const char *fPath, const int rowSize);

/*通过keyword查找*/

extern void findStringByKeyword(const char *keyword, const int rowSize);

/*查看文件里有多少行*/

extern int getFileRow(const char *path);

/*释放存放每行直至的数组的内存和每行字符串所占的内存*/

extern void freeMemory(char **pp, const int rowSize);

 

#endif

3.编写main.c

//注意文件操作相关函数的头文件是stdio.h

#include "head.h"

 

/*菜单查看*/

void main_view()

{

    system("cls");

    printf(" ******************当当用户信息查询系统******************* ");

    printf(" 1.加载数据至内存(-l) ");

    printf(" 2.查找字符串(-s) ");

    printf(" 3.释放内存(-f) ");

    printf(" *************************0.退出************************** ");

}

4.编写file.c

#define _CRT_SECURE_NO_WARNINGS

#include "head.h"

 

char **pp = NULL; //存储指针数组的地址

FILE *pf = NULL;  //定义一个文件指针

int flag = 0;     //这个标识符用于推断是否载入完毕,0:标识没有载入,1:表示完毕载入,2:表示释放释放内存

 

/*获得文件的字节大小*/

int getFileSize(const char *path)

{

    //依照读取的模式打开

    pf = fopen(path, "r");

    if (pf == NULL)

    {

        //代表获取文件失败

        return -1;

    }

    else

    {

        //fseek():Moves thefile pointer to a specified location.

        fseek(pf, 0, SEEK_END);

        //ftell( FILE*stream ):文件开头到当前位置有多少个字节

        int num = ftell(pf);

        fclose(pf);//关闭文件

        return num;

    }

}

 

/*载入文件,fPath为传递进去的文件路径*/

void loadFile(const char *fPath, const int rowSize)

{

    printf("载入文件里,请稍后....");

    //pp里面存储的是每行字符串的地址

    pp = (char **)malloc(sizeof(char *)*rowSize);

    pf = fopen(fPath, "r");

    if (pf == NULL)

    {

        printf("对不起,载入文件失败!

");

        return;

    }

    else

    {

        int i;

        for (i = 0; i < rowSize; i++)

        {

            //读取字符串的缓冲区

            char str[275] = { 0 };

            //*fgets( char*string, int n, FILE *stream );

            //从文件里逐行读取字符串

            fgets(str, 275, pf);

            //获取要分配的字符串长度,最后加一是由于''

            int strlength = strlen(str) + 1;

            //分配内存

            char *px = malloc(sizeof(char)*strlength);

            //拷贝字符串

            strcpy(px, str);

            //设定最后一个字符串为''

            px[strlength - 1] = '';

            //存储字符串的首地址到指针数组

            pp[i] = px;

        }

    }

    fclose(pf);

    flag = 1;

    printf("加载内存OK ");

}

 

/*通过keyword查找*/

void findStringByKeyword(const char *keyword, const int rowSize)

{

    if (pp == NULL)

    {

        printf("对不起。您还没有载入文件,请您先载入文件 ");

        return;

    }

    int i;

    for (i = 0; i < rowSize; i++)

    {

        //遍历全部的指针数组的地址。字符串查找

        char *ptemp = strstr(pp[i], keyword);

        if (ptemp != NULL)

        {

            printf(" %s", pp[i]);//打印字符串

        }

    }

}

 

int getFileRow(const char *path)

{

    //读取的模式打开

    pf = fopen(path, "r");

    if (pf == NULL)

    {

        //代表获取失败

        return -1;

    }

    else

    {

        int i = 0;

        //是否到文件末尾

        while (!feof(pf))

        {

            char str[275];

            fgets(str, 275, pf);//读取一行

            i++;

        }

        fclose(pf);

        return i;

    }

}

 

/*释放存放每行直至的数组的内存和每行字符串所占的内存*/

void freeMemory(char **pp, const int rowSize)

{

    printf("正在释放内存,请稍后!

");

    int i;

    for (i = 0; i < rowSize; i++)

    {

        //通过这样的方式释放内存的时候较慢,由于是一行行的释放的

        free(pp[i]);

    }

    free(pp);

    flag = 0;

}

5.编写DDSS.c

#define _CRT_SECURE_NO_WARNINGS

#include "head.h"

 

extern int flag;

extern char **pp;

 

/************************************************************************/

/* 当当用户信息查询系统                                                */

/************************************************************************/

int main(int argc, char *argv[])

{

    //文件所在位置

    char *path = "G:\dangdangwang.txt";

    int fileSize = getFileSize(path);

    //printf("%d字节,%fK,%fM", fileSize, fileSize /1024.0, fileSize / 1024.0 / 1024.0);

    //这个选择菜单是的字符串

    char choice[25];

 

    //获得行号

    int row = getFileRow(path);

    printf("%d ", row);

 

flag:system("cls");

    main_view();

    if (flag)

    {

        printf("文件载入完成,能够进行查找了! ");

    }

    else if (flag == 0)

    {

        printf("文件未载入状态,请您先载入文件! ");

    }

    while (1)

    {

        printf("输入内容或选择('-v'显示菜单):");

        scanf("%24s", choice);

 

        if (!strcmp(choice, "-v") || !strcmp(choice, "-view")){

            main_view();

        }

        else if (!strcmp(choice, "-l") || !strcmp(choice, "-loadFile"))

        {

            loadFile(path, row);

        }

        else if (!strcmp(choice, "-s") || !strcmp(choice, "-search"))

        {

            while (1)

            {

                char keyword[100] = { 0 };

                printf(" 请输入要查找的字符串,输入-exit将退出查找 ");

                scanf("%s", keyword);

 

                if (strcmp(keyword, "-exit"))

                {

                    findStringByKeyword(keyword, row);

                }

                else

                {

                    break;

                }

            }

        }

        else if (!strcmp(choice, "-f") || !strcmp(choice, "-free"))

        {

            freeMemory(pp, row);

        }

        goto flag;

    }

 

    system("pause");

    return 0;

}

 

 

 

 

将查询到的结果封装到txt文本中

#define _CRT_SECURE_NO_WARNINGS   //关闭安全检查

#include <stdio.h>

#include <stdlib.h>

 

void main()

{

    char *path = "G:\dangdangwang.txt";

    char *respath = "G:\1.txt";

 

    FILE *pf;

    FILE *fp;

    pf = fopen(path,"r");//读的模式

    fp = fopen(respath,"w");//写的模式

    if (pf == NULL)

    {

        printf("文件打开失败");

    }

    else

    {

        //文件指针到末尾

        fseek(pf, 0, SEEK_END);

        int num = ftell(pf);

        char  strinfo[200];

        sprintf(strinfo, " num=%d字节,%fK,%fM", num, num / 1024.0, num / 1024.0 / 1024.0);

        fputs(strinfo, fp);//写入文件

        rewind(pf);//回到文件开头

        while (!feof(pf))

        {

            //缓冲区

            char str[200];

            //读取。依照行读取

            fgets(str, 200, pf);

            if (strstr(str,"谭胜") != NULL)  //字符串查找

            {

                fputs(str, fp);//写入文件

                printf(" %s", str);//打印结果

            }

        }

        fclose(fp);   //关闭文件

        fclose(pf);   //关闭文件

    }

    //打开结果文件

    system(respath);

    system("pause");

}

 

原文地址:https://www.cnblogs.com/jzssuanfa/p/6945479.html