java的锁机制现行的有synchronized和Lock。
synrhronized关键字简洁、清晰、语义明确。其应用层的语义是可以把任何一个非null对象作为”锁”,当synchronized作用在方法上时,锁住的便是对象实例(this);当作用在静态方法时锁住的便是对象对应的Class实例,因为Class数据存在于永久带,因此静态方法锁相当于该类的一个全局锁;当synchronized作用于某一个对象实例时,锁住的便是对应的代码块。
synrhronized锁主要通过Lock-Free的队列,放弃了些公平性,通过自旋锁提高了瞬时的吞吐量。
下面是JAVA模拟银行账户存储和转移的实例:
1 /** 2 @version 1.30 2004-08-01 3 @author Cay Horstmann 4 */ 5 6 import java.util.concurrent.locks.*; 7 8 /** 9 This program shows how multiple threads can safely access a data structure. 10 */ 11 public class SynchBankTest 12 { 13 public static void main(String[] args) 14 { 15 Bank b = new Bank(NACCOUNTS, INITIAL_BALANCE); 16 int i; 17 for (i = 0; i < NACCOUNTS; i++) 18 { 19 TransferRunnable r = new TransferRunnable(b, i, INITIAL_BALANCE); 20 Thread t = new Thread(r); 21 t.start(); 22 } 23 } 24 25 public static final int NACCOUNTS = 100; 26 public static final double INITIAL_BALANCE = 1000; 27 } 28 29 /** 30 A bank with a number of bank accounts. 31 */ 32 class Bank 33 { 34 /** 35 Constructs the bank. 36 @param n the number of accounts 37 @param initialBalance the initial balance 38 for each account 39 */ 40 public Bank(int n, double initialBalance) 41 { 42 accounts = new double[n]; 43 for (int i = 0; i < accounts.length; i++) 44 accounts[i] = initialBalance; 45 bankLock = new ReentrantLock(); 46 sufficientFunds = bankLock.newCondition(); 47 } 48 49 /** 50 Transfers money from one account to another. 51 @param from the account to transfer from 52 @param to the account to transfer to 53 @param amount the amount to transfer 54 */ 55 public void transfer(int from, int to, double amount) 56 throws InterruptedException 57 { 58 bankLock.lock(); 59 try 60 { 61 while (accounts[from] < amount) 62 sufficientFunds.await(); 63 System.out.print(Thread.currentThread()); 64 accounts[from] -= amount; 65 System.out.printf(" %10.2f from %d to %d", amount, from, to); 66 accounts[to] += amount; 67 System.out.printf(" Total Balance: %10.2f%n", getTotalBalance()); 68 sufficientFunds.signalAll(); 69 } 70 finally 71 { 72 bankLock.unlock(); 73 } 74 } 75 76 /** 77 Gets the sum of all account balances. 78 @return the total balance 79 */ 80 public double getTotalBalance() 81 { 82 bankLock.lock(); 83 try 84 { 85 double sum = 0; 86 87 for (double a : accounts) 88 sum += a; 89 90 return sum; 91 } 92 finally 93 { 94 bankLock.unlock(); 95 } 96 } 97 98 /** 99 Gets the number of accounts in the bank. 100 @return the number of accounts 101 */ 102 public int size() 103 { 104 return accounts.length; 105 } 106 107 private final double[] accounts; 108 private Lock bankLock; 109 private Condition sufficientFunds; 110 } 111 112 /** 113 A runnable that transfers money from an account to other 114 accounts in a bank. 115 */ 116 class TransferRunnable implements Runnable 117 { 118 /** 119 Constructs a transfer runnable. 120 @param b the bank between whose account money is transferred 121 @param from the account to transfer money from 122 @param max the maximum amount of money in each transfer 123 */ 124 public TransferRunnable(Bank b, int from, double max) 125 { 126 bank = b; 127 fromAccount = from; 128 maxAmount = max; 129 } 130 131 public void run() 132 { 133 try 134 { 135 while (true) 136 { 137 int toAccount = (int) (bank.size() * Math.random()); 138 double amount = maxAmount * Math.random(); 139 bank.transfer(fromAccount, toAccount, amount); 140 Thread.sleep((int) (DELAY * Math.random())); 141 } 142 } 143 catch (InterruptedException e) {} 144 } 145 146 private Bank bank; 147 private int fromAccount; 148 private double maxAmount; 149 private int repetitions; 150 private int DELAY = 10; 151 }