fork download
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <string.h>
  4.  
  5. #define MAX_ACCOUNTS 100
  6. #define MAX_NAME_LEN 50
  7. #define MAX_TYPE_LEN 20
  8. #define MAX_HISTORY 5
  9.  
  10. struct Transaction {
  11. char type[MAX_TYPE_LEN];
  12. float amount;
  13. };
  14.  
  15. struct Account {
  16. int acc_num;
  17. char name[MAX_NAME_LEN];
  18. float balance;
  19. struct Transaction history[MAX_HISTORY];
  20. int hist_count;
  21. };
  22.  
  23. struct Bank {
  24. struct Account accounts[MAX_ACCOUNTS];
  25. int num_accounts;
  26. };
  27.  
  28. // Global bank instance
  29. struct Bank bank;
  30.  
  31. // File name for persistence
  32. #define FILENAME "accounts.dat"
  33.  
  34. // Function to save all accounts to file
  35. int save_accounts() {
  36. FILE *file = fopen(FILENAME, "wb");
  37. if (file == NULL) {
  38. printf("Error: Cannot open file for writing. Data not saved.\n");
  39. return 0; // Failure
  40. }
  41.  
  42. // Write number of accounts first
  43. fwrite(&bank.num_accounts, sizeof(int), 1, file);
  44.  
  45. // Write each account
  46. for (int i = 0; i < bank.num_accounts; i++) {
  47. fwrite(&bank.accounts[i], sizeof(struct Account), 1, file);
  48. }
  49.  
  50. printf("Accounts saved successfully.\n");
  51. return 1; // Success
  52. }
  53.  
  54. // Function to load accounts from file
  55. int load_accounts() {
  56. FILE *file = fopen(FILENAME, "rb");
  57. if (file == NULL) {
  58. printf("No existing accounts file found. Initializing with predefined accounts.\n");
  59. // Initialize with 3 predefined accounts
  60. bank.num_accounts = 3;
  61. bank.accounts[0] = (struct Account){1001, "Alice Johnson", 1000.00f, {{0}}, 0};
  62. bank.accounts[1] = (struct Account){1002, "Bob Smith", 2000.00f, {{0}}, 0};
  63. bank.accounts[2] = (struct Account){1003, "Charlie Brown", 1500.00f, {{0}}, 0};
  64. save_accounts(); // Save initial accounts
  65. return 1;
  66. }
  67.  
  68. // Read number of accounts
  69. fread(&bank.num_accounts, sizeof(int), 1, file);
  70. if (bank.num_accounts > MAX_ACCOUNTS || bank.num_accounts < 0) {
  71. printf("Error: Invalid account count in file. Initializing fresh.\n");
  72. return load_accounts(); // Recursive init
  73. }
  74.  
  75. // Read each account
  76. for (int i = 0; i < bank.num_accounts; i++) {
  77. if (fread(&bank.accounts[i], sizeof(struct Account), 1, file) != 1) {
  78. printf("Error: Failed to read account %d from file.\n", i + 1);
  79. return 0; // Failure
  80. }
  81. }
  82.  
  83. printf("Accounts loaded successfully (%d accounts).\n", bank.num_accounts);
  84. return 1; // Success
  85. }
  86.  
  87. // Function to add a transaction to history (shifts if full)
  88. void add_transaction(struct Account *acc, const char *typ, float amt) {
  89. if (acc->hist_count < MAX_HISTORY) {
  90. strcpy(acc->history[acc->hist_count].type, typ);
  91. acc->history[acc->hist_count].amount = amt;
  92. acc->hist_count++;
  93. } else {
  94. // Shift to remove oldest
  95. for (int i = 0; i < MAX_HISTORY - 1; i++) {
  96. acc->history[i] = acc->history[i + 1];
  97. }
  98. // Add new at end
  99. strcpy(acc->history[MAX_HISTORY - 1].type, typ);
  100. acc->history[MAX_HISTORY - 1].amount = amt;
  101. }
  102. }
  103.  
  104. // Function to display mini statement
  105. void display_mini_statement(struct Account *acc) {
  106. printf("\n=== Mini Statement ===\n");
  107. printf("Account Holder: %s\n", acc->name);
  108. printf("Account Number: %d\n", acc->acc_num);
  109. printf("Current Balance: $%.2f\n", acc->balance);
  110.  
  111. if (acc->hist_count == 0) {
  112. printf("No transactions yet.\n");
  113. } else {
  114. printf("Last %d Transactions (Newest to Oldest):\n", acc->hist_count);
  115. for (int i = acc->hist_count - 1; i >= 0; i--) {
  116. printf("%s: $%.2f\n", acc->history[i].type, acc->history[i].amount);
  117. }
  118. }
  119. printf("======================\n\n");
  120. }
  121.  
  122. // Function to find account by number (returns pointer or NULL)
  123. struct Account *find_account(int acc_num) {
  124. for (int i = 0; i < bank.num_accounts; i++) {
  125. if (bank.accounts[i].acc_num == acc_num) {
  126. return &bank.accounts[i];
  127. }
  128. }
  129. return NULL;
  130. }
  131.  
  132. // Function to create new account
  133. void create_account() {
  134. if (bank.num_accounts >= MAX_ACCOUNTS) {
  135. printf("Error: Maximum accounts reached. Cannot create new account.\n\n");
  136. return;
  137. }
  138.  
  139. struct Account new_acc;
  140. printf("Enter Account Number: ");
  141. if (scanf("%d", &new_acc.acc_num) != 1) {
  142. printf("Invalid input. Account creation failed.\n\n");
  143. while (getchar() != '\n'); // Clear buffer
  144. return;
  145. }
  146.  
  147. // Check for duplicate
  148. if (find_account(new_acc.acc_num) != NULL) {
  149. printf("Error: Account number already exists.\n\n");
  150. return;
  151. }
  152.  
  153. printf("Enter Account Holder Name: ");
  154. scanf(" %[^\n]", new_acc.name); // Read name with spaces
  155. printf("Enter Initial Balance: $");
  156. if (scanf("%f", &new_acc.balance) != 1 || new_acc.balance < 0) {
  157. printf("Invalid balance. Must be non-negative.\n\n");
  158. while (getchar() != '\n');
  159. return;
  160. }
  161.  
  162. new_acc.hist_count = 0; // No history yet
  163.  
  164. // Add to bank
  165. bank.accounts[bank.num_accounts] = new_acc;
  166. bank.num_accounts++;
  167.  
  168. printf("Account created successfully!\n\n");
  169. save_accounts();
  170. }
  171.  
  172. // Transaction menu for a specific account
  173. void transaction_menu(struct Account *acc) {
  174. int choice;
  175. do {
  176. printf("=== Transaction Menu (Account: %d - %s) ===\n", acc->acc_num, acc->name);
  177. printf("1. Deposit\n");
  178. printf("2. Withdrawal\n");
  179. printf("3. Mini Statement\n");
  180. printf("4. Back to Main Menu\n");
  181. printf("Enter your choice: ");
  182. if (scanf("%d", &choice) != 1) {
  183. printf("Invalid choice.\n\n");
  184. while (getchar() != '\n');
  185. continue;
  186. }
  187.  
  188. switch (choice) {
  189. case 1: {
  190. float amount;
  191. printf("Enter deposit amount: $");
  192. if (scanf("%f", &amount) == 1 && amount > 0) {
  193. acc->balance += amount;
  194. add_transaction(acc, "Deposit", amount);
  195. printf("Deposit successful! New balance: $%.2f\n\n", acc->balance);
  196. save_accounts();
  197. } else {
  198. printf("Invalid amount. Must be greater than 0.\n\n");
  199. while (getchar() != '\n');
  200. }
  201. break;
  202. }
  203. case 2: {
  204. float amount;
  205. printf("Enter withdrawal amount: $");
  206. if (scanf("%f", &amount) == 1 && amount > 0) {
  207. if (amount <= acc->balance) {
  208. acc->balance -= amount;
  209. add_transaction(acc, "Withdrawal", amount);
  210. printf("Withdrawal successful! New balance: $%.2f\n\n", acc->balance);
  211. save_accounts();
  212. } else {
  213. printf("Insufficient funds. Current balance: $%.2f\n\n", acc->balance);
  214. }
  215. } else {
  216. printf("Invalid amount. Must be greater than 0.\n\n");
  217. while (getchar() != '\n');
  218. }
  219. break;
  220. }
  221. case 3: {
  222. display_mini_statement(acc);
  223. break;
  224. }
  225. case 4:
  226. printf("Returning to main menu...\n\n");
  227. break;
  228. default:
  229. printf("Invalid choice. Please try again.\n\n");
  230. }
  231. } while (choice != 4);
  232. }
  233.  
  234. // Main function
  235. int main() {
  236. // Load accounts
  237. if (!load_accounts()) {
  238. printf("Failed to load accounts. Exiting.\n");
  239. return 1;
  240. }
  241.  
  242. printf("Welcome to the File-Based Banking System\n");
  243. printf("Predefined Accounts (if new): 1001 (Alice, $1000), 1002 (Bob, $2000), 1003 (Charlie, $1500)\n\n");
  244.  
  245. int choice;
  246. while (1) {
  247. printf("=== Main Menu ===\n");
  248. printf("1. Create New Account\n");
  249. printf("2. Access Existing Account\n");
  250. printf("3. Exit\n");
  251. printf("Enter your choice: ");
  252. if (scanf("%d", &choice) != 1) {
  253. printf("Invalid choice.\n\n");
  254. while (getchar() != '\n');
  255. continue;
  256. }
  257.  
  258. switch (choice) {
  259. case 1:
  260. create_account();
  261. break;
  262. case 2: {
  263. int acc_num;
  264. printf("Enter Account Number: ");
  265. if (scanf("%d", &acc_num) != 1) {
  266. printf("Invalid account number.\n\n");
  267. while (getchar() != '\n');
  268. break;
  269. }
  270.  
  271. struct Account *acc = find_account(acc_num);
  272. if (acc == NULL) {
  273. printf("Account not found. Create it first?\n\n");
  274. } else {
  275. printf("Welcome, %s! Your current balance: $%.2f\n\n", acc->name, acc->balance);
  276. transaction_menu(acc);
  277. }
  278. break;
  279. }
  280. case 3:
  281. printf("Saving and exiting...\n");
  282. save_accounts();
  283. printf("Thank you for using the Banking System. Goodbye!\n");
  284. return 0;
  285.  
  286. }
  287. }
  288.  
  289. return 0;
  290. }
  291.  
Success #stdin #stdout 0.02s 25512KB
stdin
Standard input is empty
stdout
#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#define MAX_ACCOUNTS 100
#define MAX_NAME_LEN 50
#define MAX_TYPE_LEN 20
#define MAX_HISTORY 5

struct Transaction {
    char type[MAX_TYPE_LEN];
    float amount;
};

struct Account {
    int acc_num;
    char name[MAX_NAME_LEN];
    float balance;
    struct Transaction history[MAX_HISTORY];
    int hist_count;
};

struct Bank {
    struct Account accounts[MAX_ACCOUNTS];
    int num_accounts;
};

// Global bank instance
struct Bank bank;

// File name for persistence
#define FILENAME "accounts.dat"

// Function to save all accounts to file
int save_accounts() {
    FILE *file = fopen(FILENAME, "wb");
    if (file == NULL) {
        printf("Error: Cannot open file for writing. Data not saved.\n");
        return 0;  // Failure
    }
    
    // Write number of accounts first
    fwrite(&bank.num_accounts, sizeof(int), 1, file);
    
    // Write each account
    for (int i = 0; i < bank.num_accounts; i++) {
        fwrite(&bank.accounts[i], sizeof(struct Account), 1, file);
    }
    
    fclose(file);
    printf("Accounts saved successfully.\n");
    return 1;  // Success
}

// Function to load accounts from file
int load_accounts() {
    FILE *file = fopen(FILENAME, "rb");
    if (file == NULL) {
        printf("No existing accounts file found. Initializing with predefined accounts.\n");
        // Initialize with 3 predefined accounts
        bank.num_accounts = 3;
        bank.accounts[0] = (struct Account){1001, "Alice Johnson", 1000.00f, {{0}}, 0};
        bank.accounts[1] = (struct Account){1002, "Bob Smith", 2000.00f, {{0}}, 0};
        bank.accounts[2] = (struct Account){1003, "Charlie Brown", 1500.00f, {{0}}, 0};
        save_accounts();  // Save initial accounts
        return 1;
    }
    
    // Read number of accounts
    fread(&bank.num_accounts, sizeof(int), 1, file);
    if (bank.num_accounts > MAX_ACCOUNTS || bank.num_accounts < 0) {
        printf("Error: Invalid account count in file. Initializing fresh.\n");
        fclose(file);
        return load_accounts();  // Recursive init
    }
    
    // Read each account
    for (int i = 0; i < bank.num_accounts; i++) {
        if (fread(&bank.accounts[i], sizeof(struct Account), 1, file) != 1) {
            printf("Error: Failed to read account %d from file.\n", i + 1);
            fclose(file);
            return 0;  // Failure
        }
    }
    
    fclose(file);
    printf("Accounts loaded successfully (%d accounts).\n", bank.num_accounts);
    return 1;  // Success
}

// Function to add a transaction to history (shifts if full)
void add_transaction(struct Account *acc, const char *typ, float amt) {
    if (acc->hist_count < MAX_HISTORY) {
        strcpy(acc->history[acc->hist_count].type, typ);
        acc->history[acc->hist_count].amount = amt;
        acc->hist_count++;
    } else {
        // Shift to remove oldest
        for (int i = 0; i < MAX_HISTORY - 1; i++) {
            acc->history[i] = acc->history[i + 1];
        }
        // Add new at end
        strcpy(acc->history[MAX_HISTORY - 1].type, typ);
        acc->history[MAX_HISTORY - 1].amount = amt;
    }
}

// Function to display mini statement
void display_mini_statement(struct Account *acc) {
    printf("\n=== Mini Statement ===\n");
    printf("Account Holder: %s\n", acc->name);
    printf("Account Number: %d\n", acc->acc_num);
    printf("Current Balance: $%.2f\n", acc->balance);
    
    if (acc->hist_count == 0) {
        printf("No transactions yet.\n");
    } else {
        printf("Last %d Transactions (Newest to Oldest):\n", acc->hist_count);
        for (int i = acc->hist_count - 1; i >= 0; i--) {
            printf("%s: $%.2f\n", acc->history[i].type, acc->history[i].amount);
        }
    }
    printf("======================\n\n");
}

// Function to find account by number (returns pointer or NULL)
struct Account *find_account(int acc_num) {
    for (int i = 0; i < bank.num_accounts; i++) {
        if (bank.accounts[i].acc_num == acc_num) {
            return &bank.accounts[i];
        }
    }
    return NULL;
}

// Function to create new account
void create_account() {
    if (bank.num_accounts >= MAX_ACCOUNTS) {
        printf("Error: Maximum accounts reached. Cannot create new account.\n\n");
        return;
    }
    
    struct Account new_acc;
    printf("Enter Account Number: ");
    if (scanf("%d", &new_acc.acc_num) != 1) {
        printf("Invalid input. Account creation failed.\n\n");
        while (getchar() != '\n');  // Clear buffer
        return;
    }
    
    // Check for duplicate
    if (find_account(new_acc.acc_num) != NULL) {
        printf("Error: Account number already exists.\n\n");
        return;
    }
    
    printf("Enter Account Holder Name: ");
    scanf(" %[^\n]", new_acc.name);  // Read name with spaces
    printf("Enter Initial Balance: $");
    if (scanf("%f", &new_acc.balance) != 1 || new_acc.balance < 0) {
        printf("Invalid balance. Must be non-negative.\n\n");
        while (getchar() != '\n');
        return;
    }
    
    new_acc.hist_count = 0;  // No history yet
    
    // Add to bank
    bank.accounts[bank.num_accounts] = new_acc;
    bank.num_accounts++;
    
    printf("Account created successfully!\n\n");
    save_accounts();
}

// Transaction menu for a specific account
void transaction_menu(struct Account *acc) {
    int choice;
    do {
        printf("=== Transaction Menu (Account: %d - %s) ===\n", acc->acc_num, acc->name);
        printf("1. Deposit\n");
        printf("2. Withdrawal\n");
        printf("3. Mini Statement\n");
        printf("4. Back to Main Menu\n");
        printf("Enter your choice: ");
        if (scanf("%d", &choice) != 1) {
            printf("Invalid choice.\n\n");
            while (getchar() != '\n');
            continue;
        }
        
        switch (choice) {
            case 1: {
                float amount;
                printf("Enter deposit amount: $");
                if (scanf("%f", &amount) == 1 && amount > 0) {
                    acc->balance += amount;
                    add_transaction(acc, "Deposit", amount);
                    printf("Deposit successful! New balance: $%.2f\n\n", acc->balance);
                    save_accounts();
                } else {
                    printf("Invalid amount. Must be greater than 0.\n\n");
                    while (getchar() != '\n');
                }
                break;
            }
            case 2: {
                float amount;
                printf("Enter withdrawal amount: $");
                if (scanf("%f", &amount) == 1 && amount > 0) {
                    if (amount <= acc->balance) {
                        acc->balance -= amount;
                        add_transaction(acc, "Withdrawal", amount);
                        printf("Withdrawal successful! New balance: $%.2f\n\n", acc->balance);
                        save_accounts();
                    } else {
                        printf("Insufficient funds. Current balance: $%.2f\n\n", acc->balance);
                    }
                } else {
                    printf("Invalid amount. Must be greater than 0.\n\n");
                    while (getchar() != '\n');
                }
                break;
            }
            case 3: {
                display_mini_statement(acc);
                break;
            }
            case 4:
                printf("Returning to main menu...\n\n");
                break;
            default:
                printf("Invalid choice. Please try again.\n\n");
        }
    } while (choice != 4);
}

// Main function
int main() {
    // Load accounts
    if (!load_accounts()) {
        printf("Failed to load accounts. Exiting.\n");
        return 1;
    }
    
    printf("Welcome to the File-Based Banking System\n");
    printf("Predefined Accounts (if new): 1001 (Alice, $1000), 1002 (Bob, $2000), 1003 (Charlie, $1500)\n\n");
    
    int choice;
    while (1) {
        printf("=== Main Menu ===\n");
        printf("1. Create New Account\n");
        printf("2. Access Existing Account\n");
        printf("3. Exit\n");
        printf("Enter your choice: ");
        if (scanf("%d", &choice) != 1) {
            printf("Invalid choice.\n\n");
            while (getchar() != '\n');
            continue;
        }
        
        switch (choice) {
            case 1:
                create_account();
                break;
            case 2: {
                int acc_num;
                printf("Enter Account Number: ");
                if (scanf("%d", &acc_num) != 1) {
                    printf("Invalid account number.\n\n");
                    while (getchar() != '\n');
                    break;
                }
                
                struct Account *acc = find_account(acc_num);
                if (acc == NULL) {
                    printf("Account not found. Create it first?\n\n");
                } else {
                    printf("Welcome, %s! Your current balance: $%.2f\n\n", acc->name, acc->balance);
                    transaction_menu(acc);
                }
                break;
            }
            case 3:
                printf("Saving and exiting...\n");
                save_accounts();
                printf("Thank you for using the Banking System. Goodbye!\n");
                return 0;
        
        }
    }
    
    return 0;
}