Java
February 9

Concurrent Bank Transaction System in Java

Below is an example of a concurrent bank transaction system in Java. In this example, we model a bank account with methods for deposit, withdrawal, and a transfer operation that involves two accounts. We use a ReentrantLock in each account to ensure that modifications to the account balance are thread-safe, and we take care to avoid deadlocks when transferring funds between two accounts.

BankAccount Class:

  • Fields & Lock:
    Each account has a unique id, a balance, and a dedicated ReentrantLock to protect its state.
  • Deposit & Withdraw:
    The methods deposit() and withdraw() lock the account before modifying the balance to ensure thread safety.
  • Transfer Method:
    The static transfer() method transfers funds between two accounts.
    • To prevent deadlocks when acquiring two locks (one for each account), we always lock the accounts in a fixed order based on their IDs.
    • Once both locks are acquired, the method checks for sufficient funds, performs the transfer, and then unlocks both accounts.

(Main Simulation):

    • ExecutorService:
      We use a fixed thread pool to simulate concurrent transactions.
    • Tasks:
      Three tasks are created to transfer funds between the accounts:
      • Task 1 transfers money from Account 1 to Account 2.
      • Task 2 transfers money from Account 2 to Account 1.
    • Shutdown & Final Output:
      The executor is shut down gracefully after submitting the tasks, and once all tasks complete, the final balances of each account are printed.

This example demonstrates key concurrency concepts in a real-world banking scenario, including proper synchronization with locks, avoiding deadlock by enforcing a lock order, and managing concurrent tasks using an ExecutorService.