小内存大数据排序-[多路归并法][文件一些的操作]

总结一下几个文件操作注意点。

  1. 新打开文件时注意括号
    注意 赋值= 的优先级低于 比较==
    一定要
(fp = fopen("in.txt", "r")) == NULL
  1. 注意一些惯用操作
FILE* fp;
	if ((fp = fopen("in.txt", "r")) == NULL) printf("Open Fail.");
	else  {
		for(i = 0; i <= 99; i++){
			fscanf(fp, "%d", &(a[j++]));
		}
	}
	fclose(fp);
  1. 明确六种打开模式
    r: 打开一个已有文件,只能读,位置指针默认在开头
    r+:打开一个已有文件,可以读写,位置指针默认在开头
    a: 打开一个已有文件,只能写,位置指针默认在结尾
    a+:打开一个已有文件,可以读写,位置指针默认在结尾
    w: 新建一个文件,只能写,位置指针默认在开头。(新建时覆盖原有文件)
    w+:新建一个文件,可以读写,位置指针默认在开头。(新建时覆盖原有文件)

题目-小内存大数据排序

假设内存中最多可以存100个正整数,实现一个排序方法,可以对包含1000个正整数的磁盘文件进行排序。这里假设排序操作只能在内存中进行。

#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <errno.h>	//与文件删除的查错有关的库
#define MAXN 99999

void ReadFile(int* a, int num);
void QuickSort(int* a, int low, int high);
void GuiBing(FILE** fparr, int* a);
FILE* OutputFile(int* a, int num);
void Remove1(FILE** fparr);
int main(void)
{
	int i;
	int a[100];
	FILE* fparr[10];

	for (i = 0; i <= 9; i++) {
		ReadFile(a, i);
		QuickSort(a, 0, 99);
		fparr[i] = OutputFile(a, i);
	}	
	GuiBing(fparr, a);
	Remove1(fparr);
	
	return 0;
}

void GuiBing(FILE** fparr, int* a)
{	
	FILE* fpout;
	if ((fpout = fopen("out.txt", "w")) == NULL)
		printf("Open out.txt fail.");

	int i, amin, cnt = 0;
	for (i = 0; i <= 9; i++) {//读入每组第一个数
		fscanf(fparr[i], "%d", &(a[i]));
	}

	while (cnt != 1000) {
		amin = a[0];
		for (i = 1; i <= 9; i++) {//找到a中最小的
			amin = min(a[i], amin);
		}
		for (i = 0; i <= 9; i++) {
			if (a[i] == amin) {
				fprintf(fpout, "%d ", amin);  cnt++;
				if (!feof(fparr[i])) { fscanf(fparr[i], "%d ", &(a[i])); }
				else { a[i] = MAXN; }
				break;
			}
		}
	}
	fclose(fpout);
	return;
}

void ReadFile(int* a, int num)//num是第几组(从0开始)
{
	int i = 0, j = 0;
	FILE* fp;
	if ((fp = fopen("in.txt", "r")) == NULL) printf("Open Fail.");
	else {
		for(i = 0; i <= 999; i++){
			if (i >= num * 10 && i <= num * 10 + 99) fscanf(fp, "%d", &(a[j++]));
		}
	}
	fclose(fp);
	return;
}

FILE* OutputFile(int* a, int num)
{
	int i = 0;
	FILE* fp = NULL;
	if (num == 0) { if ((fp = fopen("out0.txt", "w+")) == NULL) printf("Output Fail."); }
	if (num == 1) { if ((fp = fopen("out1.txt", "w+")) == NULL) printf("Output Fail."); }
	if (num == 2) { if ((fp = fopen("out2.txt", "w+")) == NULL) printf("Output Fail."); }
	if (num == 3) { if ((fp = fopen("out3.txt", "w+")) == NULL) printf("Output Fail."); }
	if (num == 4) { if ((fp = fopen("out4.txt", "w+")) == NULL) printf("Output Fail."); }
	if (num == 5) { if ((fp = fopen("out5.txt", "w+")) == NULL) printf("Output Fail."); }
	if (num == 6) { if ((fp = fopen("out6.txt", "w+")) == NULL) printf("Output Fail."); }
	if (num == 7) { if ((fp = fopen("out7.txt", "w+")) == NULL) printf("Output Fail."); }
	if (num == 8) { if ((fp = fopen("out8.txt", "w+")) == NULL) printf("Output Fail."); }
	if (num == 9) { if ((fp = fopen("out9.txt", "w+")) == NULL) printf("Output Fail."); }

	for(i = 0; i <= 99; i++){
		fprintf(fp, "%d ", a[i]);
	}
	//fclose(fp);
	rewind(fp);			//可以rewind文件指针,来让文件位置指针回到开头
	return fp;
}

void Remove1(FILE** fparr) 
{
	int err0;
	
	fclose(fparr[0]);
	err0 = remove("out0.txt");				//文件删除函数
	if (err0 == -1) perror("remove");		//这是一种查错方法,若删除失败可以知道原因
	
	fclose(fparr[1]); remove("out1.txt");	//与手动删除相同,没关闭的文件是不能删除的
	fclose(fparr[2]); remove("out2.txt");	//另外,只读文件也不能删除
	fclose(fparr[3]); remove("out3.txt");
	fclose(fparr[4]); remove("out4.txt");
	fclose(fparr[5]); remove("out5.txt");
	fclose(fparr[6]); remove("out6.txt");
	fclose(fparr[7]); remove("out7.txt");
	fclose(fparr[8]); remove("out8.txt");
	fclose(fparr[9]); remove("out9.txt");

}

void QuickSort(int* a, int low, int high)
{
	int i = low, j = high;
	int key = a[low];
	
	if (low >= high)return;

	while (i < j) {
		while (i < j&&a[j] >= key) j--;
		a[i] = a[j];
		while (i < j&&a[i] <= key) i++;
		a[j] = a[i];
	}
	a[i] = key;

	QuickSort(a, low, i - 1);
	QuickSort(a, i + 1, high);
	return;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值