根据用户输入的账号和密码,判断用户是否合法,如果是合法用户则记录用户的账号、上机实践,如果为非法用户则提示账号或密码错误,请重试。用户上机结束后,记录用户的下机时间并计算费用(设每小时时间费用为1元)。
用两个文件存放
定义两个结构体。
下面是一个C语言的示例程序,可以实现用户登录验证和记录用户上机和下机时间,并计算上机时间和费用,并将记录写入两个文件中。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#define MAX_USER 100 // 最大用户数
#define MAX_NAME 20 // 用户名最大长度
#define MAX_PASS 20 // 密码最大长度
// 用户结构体
typedef struct {
char name[MAX_NAME];
char pass[MAX_PASS];
time_t start_time; // 上机时间
time_t end_time; // 下机时间
} User;
// 用户管理结构体
typedef struct {
User users[MAX_USER];
int count; // 当前用户数
} UserManager;
// 初始化用户管理器
void init_user_manager(UserManager *manager) {
manager->count = 0;
}
// 添加用户
void add_user(UserManager *manager, const char *name, const char *pass) {
if (manager->count >= MAX_USER) {
printf("Error: Too many users.\n");
return;
}
User *user = &manager->users[manager->count];
strcpy(user->name, name);
strcpy(user->pass, pass);
user->start_time = 0;
user->end_time = 0;
manager->count++;
}
// 查找用户
User *find_user(UserManager *manager, const char *name) {
for (int i = 0; i < manager->count; i++) {
if (strcmp(manager->users[i].name, name) == 0) {
return &manager->users[i];
}
}
return NULL;
}
// 记录用户上机时间
void logon_user(UserManager *manager, const char *name) {
User *user = find_user(manager, name);
if (user == NULL) {
printf("Error: Invalid user.\n");
return;
}
if (user->start_time != 0) {
printf("Error: User already logged on.\n");
return;
}
user->start_time = time(NULL);
printf("User '%s' logged on at %s", user->name, ctime(&user->start_time));
}
// 记录用户下机时间,并计算费用
void logoff_user(UserManager *manager, const char *name) {
User *user = find_user(manager, name);
if (user == NULL) {
printf("Error: Invalid user.\n");
return;
}
if (user->start_time == 0) {
printf("Error: User has not logged on.\n");
return;
}
user->end_time = time(NULL);
double duration = difftime(user->end_time, user->start_time);
double cost = duration / 3600;
printf("User '%s' logged off at %s", user->name, ctime(&user->end_time));
printf("User '%s' used the computer for %.1f hours, and the cost is %.1f yuan.\n", user->name, duration / 3600, cost);
// 将记录写入文件
FILE *log_file = fopen("log.txt", "a");
fprintf(log_file, "User '%s' logged on at %s", user->name, ctime(&user->start_time));
fprintf(log_file, "User '%s' logged off at %s", user->name, ctime(&user->end_time));
fprintf(log_file, "User '%s' used the computer for %.1f hours, and the cost is %.1f yuan.\n\n", user->name, duration / 3600, cost);
fclose(log_file);
// 重置用户状态
user->start_time = 0;
user->end_time = 0;
}
int main() {
UserManager manager;
init_user_manager(&manager);
// 从文件中读取用户信息
FILE *user_file = fopen("user.txt", "r");
char name[MAX_NAME];
char pass[MAX_PASS];
while (fscanf(user_file, "%s %s", name, pass) != EOF) {
add_user(&manager, name, pass);
}
fclose(user_file);
// 进入命令行交互模式
while (1) {
printf("Please enter username and password, separated by a space (q to quit): ");
char name[MAX_NAME];
char pass[MAX_PASS];
scanf("%s", name);
if (strcmp(name, "q") == 0) {
break;
}
scanf("%s", pass);
User *user = find_user(&manager, name);
if (user == NULL || strcmp(user->pass, pass) != 0) {
printf("Invalid username or password. Please try again.\n");
} else {
logon_user(&manager, name);
printf("Welcome, %s!\n", name);
while (1) {
printf("Enter 'logoff' to log off (q to quit): ");
char command[10];
scanf("%s", command);
if (strcmp(command, "logoff") == 0) {
logoff_user(&manager, name);
break;
} else if (strcmp(command, "q") == 0) {
logoff_user(&manager, name);
break;
} else {
printf("Invalid command. Please try again.\n");
}
}
}
}
return 0;
}
这段代码中,首先在logoff_user函数中打开一个名为log.txt的文件,并将用户上机和下机的时间、使用时间和费用写入文件中。然后关闭文件,并在函数末尾将用户状态重置。
然后在main函数中,首先从user.txt文件中读取用户信息,然后进入命令行交互模式,接收用户输入的用户名和密码,进行验证。如果验证通过,则调用logon_user函数记录用户上机时间,并进入循环等待用户输入下机指令。如果用户输入了logoff指令,则调用logoff_user函数记录用户下机时间,并退出循环。如果用户输入了q指令,则调用logoff_user函数记录用户下机时间,并退出循环,程序结束。如果用户输入了其他指令,则提示用户指令无效,并等待用户继续输入。
下面是一个简单的C语言程序,使用结构体和文件实现机房上机模拟系统:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#define MAX_USERS 100
#define MAX_NAME_LEN 20
#define MAX_PASSWORD_LEN 20
// 定义用户结构体
typedef struct {
char name[MAX_NAME_LEN];
char password[MAX_PASSWORD_LEN];
int is_valid; // 是否合法用户的标志
} User;
// 定义上机记录结构体
typedef struct {
char name[MAX_NAME_LEN];
time_t login_time;
time_t logout_time;
} Record;
// 全局变量
User users[MAX_USERS];
int num_users = 0;
Record records[MAX_USERS];
int num_records = 0;
// 函数声明
void load_users(char *filename);
void save_users(char *filename);
void load_records(char *filename);
void save_records(char *filename);
int login();
void logout(int index);
void print_records();
int main() {
load_users("users.txt");
load_records("records.txt");
while (1) {
int choice;
printf("1. 登录\n2. 退出\n");
printf("请输入选项:");
scanf("%d", &choice);
if (choice == 1) {
int index = login();
if (index >= 0) {
printf("登录成功!\n");
printf("1. 上机\n2. 下机\n");
printf("请输入选项:");
scanf("%d", &choice);
if (choice == 1) {
time_t now = time(NULL);
records[num_records].login_time = now;
strcpy(records[num_records].name, users[index].name);
num_records++;
printf("上机成功!\n");
} else if (choice == 2) {
logout(index);
}
} else {
printf("账号或密码错误,请重试!\n");
}
} else if (choice == 2) {
break;
}
}
save_users("users.txt");
save_records("records.txt");
print_records();
return 0;
}
// 加载用户信息
void load_users(char *filename) {
FILE *fp = fopen(filename, "r");
if (fp) {
while (fscanf(fp, "%s %s %d", users[num_users].name, users[num_users].password, &users[num_users].is_valid) == 3) {
num_users++;
}
fclose(fp);
}
}
// 保存用户信息
void save_users(char *filename) {
FILE *fp = fopen(filename, "w");
if (fp) {
for (int i = 0; i < num_users; i++) {
fprintf(fp, "%s %s %d\n", users[i].name, users[i].password, users[i].is_valid);
}
fclose(fp);
}
}
// 加载上机记录
void load_records(char *filename) {
FILE *fp = fopen(filename, "r");
if (fp) {
while (fscanf(fp, "%s %ld %ld", records[num_records].name, &records[num_records].login_time, &records[num_records].logout_time) == 3) {
num_records++;
}
fclose(fp);
}
}
// 保存上机记录
void save_records(char *filename) {
FILE *fp = fopen(filename, "w");
if(fp) {
for (int i = 0; i < num_records; i++) {
fprintf(fp, "%s %ld %ld\n", records[i].name, records[i].login_time, records[i].logout_time);
}
fclose(fp);
}
}
// 登录
int login() {
char name[MAX_NAME_LEN];
char password[MAX_PASSWORD_LEN];
printf("请输入用户名:");
scanf("%s", name);
printf("请输入密码:");
scanf("%s", password);
for (int i = 0; i < num_users; i++) {
if (strcmp(users[i].name, name) == 0 && strcmp(users[i].password, password) == 0 && users[i].is_valid) {
return i;
}
}
return -1;
}
// 下机
void logout(int index) {
time_t now = time(NULL);
for (int i = num_records - 1; i >= 0; i--) {
if (strcmp(records[i].name, users[index].name) == 0 && records[i].logout_time == 0) {
records[i].logout_time = now;
printf("下机成功!\n");
printf("本次上机时间为:%ld 秒\n", (long)(records[i].logout_time - records[i].login_time));
int cost = (int)((records[i].logout_time - records[i].login_time) / 3600);
printf("本次费用为:%d 元\n", cost);
return;
}
}
printf("您还没有上机,请先上机!\n");
}
// 打印上机记录
void print_records() {
printf("上机记录:\n");
for (int i = 0; i < num_records; i++) {
printf("%s 上机时间:%s 下机时间:%s\n", records[i].name, ctime(&records[i].login_time), ctime(&records[i].logout_time));
}
}
上面的代码定义了两个结构体,User 和 Record,分别用于存放用户信息和上机记录。load_users、save_users、load_records、save_records 四个函数用于加载和保存用户信息和上机记录,这里使用了文件操作来读写文件。
login 函数用于登录,根据用户输入的账号和密码,遍历用户数组,如果找到合法的用户则返回该用户的索引,否则返回 -1。
logout 函数用于下机,根据用户的索引遍历上机记录数组,找到最近的一条记录并将其下机时间设置为当前时间,计算费用并输出。
print_records 函数用于打印所有的上机记录。
在主函数中,使用一个循环来不断接受用户输入的选项,如果用户选择登录,则调用 login 函数进行登录,如果登录成功则再次接受用户输入的选项,如果是上机,则记录上机时间,如果是下机,则调用 logout 函数进行下机操作。如果用户选择退出,则跳出循环。
最后,在程序结束前,调用 save_users 和 save_records 函数将用户信息和上机记录保存到文件中,并调用 print_records 函数打