Without a defined delimiter in the file (such as comma or semicolon) to separate the fields, try printing the file based on the width of each member.
(在文件中没有定义的分隔符(例如逗号或分号)中,以分隔字段,请尝试根据每个成员的宽度打印文件。)
id has a size of 20 so use "%-*s"
to print to the file. (id的大小为20,因此请使用"%-*s"
打印到文件。)
The asterisk allows for a variable as the width and the minus is to left justify. (星号允许变量为宽度,负号表示正负。)
When reading, the width is now known so use strncpy
to copy the width number of characters and trimtrailing
to remove the trailing whitespace.
(读取时,宽度现在是已知的,因此使用strncpy
复制宽度的字符数,并使用trimtrailing
删除尾随的空格。)
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#define ID 20
#define FNAME 50
#define LNAME 20
#define GENDER 3
#define DEPARTMENT 30
#define IC 16
#define EMAIL 30
#define PHONE 14
#define ADDRESS 30
struct staffinfo {
char id[ID];
char fname[FNAME];
char lname[LNAME];
char gender[GENDER];
char department[DEPARTMENT];
char ic[IC];
char email[EMAIL];
char phone[PHONE];
char address[ADDRESS];
};
int fgetsline ( char *line, size_t len, FILE *fin) {
do {
if ( 'x01' == line[0]) {
printf ( "Too many characters. Try again.
");
}
if ( '
' == line[0]) {
printf ( "Try again.
");
}
if ( fgets ( line, len, fin)) {
if ( !strchr ( line, '
')) {//no newline
while ( !strchr ( line, '
')) {//call until newline is found. clears input
if ( ! fgets ( line, len, fin)) {
fprintf ( stderr, "
fgets EOF
");
return 0;
}
}
line[0] = 'x01';//unlikely to be a valid character
}
}
else {
fprintf ( stderr, "
fgets EOF
");
return 0;
}
} while ( 'x01' == line[0] || '
' == line[0]);
line[strcspn ( line, "
")] = 0;//remove newline
return 1;
}
void trimtrailing ( char *str) {
char *temp = str;
while ( str && *temp) {//not zero
temp++;
}
if ( temp > str) {
temp--;//character before zero
}
while ( temp > str && isspace ( *temp)) {
*temp = 0;
temp--;
}
}
int main ( void) {
struct staffinfo newStaff = { 0};
printf ( "ID:");
fflush ( stdout);//no newline in printf so force output
if ( ! fgetsline ( newStaff.id, sizeof newStaff.id, stdin)) {
exit ( EXIT_FAILURE);
}
printf ( "First name:");
fflush ( stdout);//no newline in printf so force output
if ( ! fgetsline ( newStaff.fname, sizeof newStaff.fname, stdin)) {
exit ( EXIT_FAILURE);
}
printf ( "Last name:");
fflush ( stdout);//no newline in printf so force output
if ( ! fgetsline ( newStaff.lname, sizeof newStaff.lname, stdin)) {
exit ( EXIT_FAILURE);
}
printf ( "Gender (M/F):");
fflush ( stdout);//no newline in printf so force output
if ( ! fgetsline ( newStaff.gender, sizeof newStaff.gender, stdin)) {
exit ( EXIT_FAILURE);
}
printf ( "Deparment:");
fflush ( stdout);//no newline in printf so force output
if ( ! fgetsline ( newStaff.department, sizeof newStaff.department, stdin)) {
exit ( EXIT_FAILURE);
}
printf ( "NRIC:");
fflush ( stdout);//no newline in printf so force output
if ( ! fgetsline ( newStaff.ic, sizeof newStaff.ic, stdin)) {
exit ( EXIT_FAILURE);
}
printf ( "Email:");
fflush ( stdout);//no newline in printf so force output
if ( ! fgetsline ( newStaff.email, sizeof newStaff.email, stdin)) {
exit ( EXIT_FAILURE);
}
printf ( "Mobile No.:");
fflush ( stdout);//no newline in printf so force output
if ( ! fgetsline ( newStaff.phone, sizeof newStaff.phone, stdin)) {
exit ( EXIT_FAILURE);
}
printf ( "Address:");
fflush ( stdout);//no newline in printf so force output
if ( ! fgetsline ( newStaff.address, sizeof newStaff.address, stdin)) {
exit ( EXIT_FAILURE);
}
FILE *pf = NULL;
if ( NULL == ( pf = fopen ( "afile.txt", "a"))) {
perror ( "afile.txt");
exit ( EXIT_FAILURE);
}
fprintf ( pf, "%-*s", ID, newStaff.id);//print at least ID characters left justified
fprintf ( pf, "%-*s", FNAME, newStaff.fname);
fprintf ( pf, "%-*s", LNAME, newStaff.lname);
fprintf ( pf, "%-*s", GENDER, newStaff.gender);
fprintf ( pf, "%-*s", DEPARTMENT, newStaff.department);
fprintf ( pf, "%-*s", IC, newStaff.ic);
fprintf ( pf, "%-*s", EMAIL, newStaff.email);
fprintf ( pf, "%-*s", PHONE, newStaff.phone);
fprintf ( pf, "%-*s
", ADDRESS, newStaff.address);
fclose ( pf);
if ( NULL == ( pf = fopen ( "afile.txt", "r"))) {
perror ( "afile.txt");
exit ( EXIT_FAILURE);
}
char line[1024] = "";
char item[1024] = "";
while ( fgetsline ( line, sizeof line, pf)) {
int len = strlen ( line);
int offset = 0;
strncpy ( item, line + offset, ID - 1);
item[ID - 1] = 0;
trimtrailing ( item);
printf ( "ID: %s
", item);
offset += ID;
if ( offset >= len) {
continue;
}
strncpy ( item, line + offset, FNAME - 1);
item[FNAME - 1] = 0;
trimtrailing ( item);
printf ( "FNAME: %s
", item);
offset += FNAME;
if ( offset >= len) {
continue;
}
strncpy ( item, line + offset, LNAME - 1);
item[LNAME - 1] = 0;
trimtrailing ( item);
printf ( "LNAME: %s
", item);
offset += LNAME;
if ( offset >= len) {
continue;
}
strncpy ( item, line + offset, GENDER - 1);
item[GENDER - 1] = 0;
trimtrailing ( item);
printf ( "GENDER: %s
", item);
offset += GENDER;
if ( offset >= len) {
continue;
}
strncpy ( item, line + offset, DEPARTMENT - 1);
item[DEPARTMENT - 1] = 0;
trimtrailing ( item);
printf ( "DEPARTMENT: %s
", item);
offset += DEPARTMENT;
if ( offset >= len) {
continue;
}
strncpy ( item, line + offset, IC - 1);
item[IC - 1] = 0;
trimtrailing ( item);
printf ( "IC: %s
", item);
offset += IC;
if ( offset >= len) {
continue;
}
strncpy ( item, line + offset, EMAIL - 1);
item[EMAIL - 1] = 0;
trimtrailing ( item);
printf ( "EMAIL: %s
", item);
offset += EMAIL;
if ( offset >= len) {
continue;
}
strncpy ( item, line + offset, PHONE - 1);
item[PHONE - 1] = 0;
trimtrailing ( item);
printf ( "PHONE: %s
", item);
offset += PHONE;
if ( offset >= len) {
continue;
}
strncpy ( item, line + offset, ADDRESS - 1);
item[ADDRESS - 1] = 0;
trimtrailing ( item);
printf ( "ADDRESS: %s
", item);
}
fclose ( pf);
return 0;
}