Think in java 答案_Chapter 5_Exercise 11

阅前声明: http://blog.csdn.net/heimaoxiaozi/archive/2007/01/19/1487884.aspx



/****************** Exercise 11 *****************
* Following the form of the example Lunch.java,
* create a class called ConnectionManager that
* manages a fixed array of Connection objects.
* The client programmer must not be able to
* explicitly create Connection objects, but can
* only get them via a static method in
* ConnectionManager. When the ConnectionManager
* runs out of objects, it returns a null
* reference. Test the classes in main().
***********************************************/

import c05.connection.*;
public class E11_ConnectionManager {
  public static void main(String args[]) {
    Connection c =
      ConnectionManager.getConnection();
    while(c != null) {
      System.out.println(c);
      c.doSomething();
      c = ConnectionManager.getConnection();
    }
  }
}

 //+M java E11_ConnectionManager

 

package c05.connection;
public class Connection {
  private static int counter = 0;
  private int id = counter++;
  Connection() {}
  public String toString() {
    return "Connection " + id;
  }
  public void doSomething() {}
}



package c05.connection;
public class ConnectionManager {
  private static Connection[] pool =
    new Connection[10];
  private static int counter = 0;
  static {
    for(int i = 0; i < pool.length; i++)
      pool[i] = new Connection();
  }
  // Very simple -- just hands out each one once:
  public static Connection getConnection() {
    if(counter < pool.length)
      return pool[counter++];
    return null;
  }
}

**The Connection class uses a static int called counter to automatically give each Connection object an identifier, which it will produce as part of it’s toString( ) representation. Connection also has a doSomething( ) method, which is presumably the useful work that motivates you to use the Connection object.

**Note that the constructor for Connection is “friendly,” so it is unavailable outside of this package. Thus, the client programmer is unable to access that constructor and cannot make instances of Connection directly. The only way to get Connection objects is through the ConnectionManager.

**In the ConnectionManager, a static array of objects is initialized inside the static clause, which is only called once when the class is loaded (you can look up further details on static clauses in the book). In this version of the solution, the connection manager is trivial, since it only produces each Connection object in the array once.

**You might want to create a slightly more sophisticated connection manager by allowing a connection to be checked back in when the client programmer is finished with it. Here’s one way to accomplish this:


// Connections that can be checked in.
import c05.connection2.*;
public class E11_ConnectionManager2 {
  public static void main(String args[]) {
    Connection[] ca = new Connection[10];
    // Use up all the connections
    for(int i = 0; i < 10; i++)
      ca[i] = ConnectionManager.getConnection();
    // Should produce "null" since there are no
    // more connections:
    System.out.println(
      ConnectionManager.getConnection());
    // Return connections, then get them out:
    for(int i = 0; i < 5; i++) {
      ca[i].checkIn();
      Connection c =
        ConnectionManager.getConnection();
      System.out.println(c);
      c.doSomething();
      c.checkIn();
    }
  }
}

//+M java E11_ConnectionManager2


package c05.connection2;
public class Connection {
  private static int counter = 0;
  private int id = counter++;
  Connection() {}
  public String toString() {
    return "Connection " + id;
  }
  public void doSomething() {}
  public void checkIn() {
    ConnectionManager.checkIn(this);
  }
}


package c05.connection2;
public class ConnectionManager {
  private static Connection[] pool =
    new Connection[10];
  static {
    for(int i = 0; i < pool.length; i++)
      pool[i] = new Connection();
  }
  // Produce the first available connection:
  public static Connection getConnection() {
    for(int i = 0; i < pool.length; i++)
      if(pool[i] !=null) {
        Connection c = pool[i];
        pool[i] = null;// Indicates "in use"
        return c;
      }
    return null; // None left
  }
  public static void checkIn(Connection c) {
    for(int i = 0; i < pool.length; i++)
      if(pool[i] ==null) {
        pool[i] = c; // Check it back in
        return;
      }
  }
}

**

When a Connection is checked out, its slot in pool is set to null. When the client programmer is done with the connection, checkIn( ) will return it to the connection pool by finding a null slot in pool and assigning it there.

**Of course, there are all kinds of problems with this approach. What if a client checks a Connection in and then continues to use it? What if they check it in more than once? The book Thinking in Patterns (available from www.BruceEckel.com) has a more thorough coverage of the problem of the connection pool.

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值