将静态字段传递给线程

时间:2012-04-18 21:28:07

标签: java multithreading static final

我用Java编写了一个小型HTTP服务器,我在将静态变量(服务器配置:端口,root等)传递给处理请求的线程时遇到了问题。我不希望我的线程修改这些变量,如果它扩展了服务器类,它也将继承我不想要的方法。

出于性能原因,我不想使用getter。如果我将静态成员设为final,那么从配置文件加载它们时我会遇到问题。

这是一个例子

class HTTPServer {
static int port; 
static File root;
etc..
....
//must be public
public void launch() throws HTTPServerException {
    loadConfig();
    while (!pool.isShutdown()) {
            ....
        //using some config here
             ...
        try {
    Socket s = ss.accept();
    Worker w = new Worker(s);
    pool.execute(w);
        }catch () {...}
    }
}
private void loadConfig(){ //reading from file};
...
other methods that must be public goes here
}

我也不希望将worker作为嵌套类。它在另一个包中......

你有什么建议?

2 个答案:

答案 0 :(得分:2)

您可以将配置放入最终AtomicReference。然后它可以由您的工作人员引用,也可以以线程安全的方式更新。

类似的东西:

class HTTPServer {
  public static final AtomicReference<ServerConf> config = 
    new AtomicReference(new ServerConf());
}

使新的ServerConf类不可变:

class ServerConf {
  final int port;
  final File root;
  public ServerConf(int port, File root) {
    this.port = port;
    this.root = root;
  } 
}

然后,您的工作人员可以通过HTTPServer.config.get()获取对当前配置的引用。也许是这样的事情:

Worker w = new Worker(s, HTTPServer.config.get());

loadConfig()可以通过以下内容设置新配置:

HTTPServer.config.set(new ServerConf(8080, new File("/foo/bar"));

如果同时更改所有配置并不重要,则可以跳过ServerConf类并使用AtomicInteger作为端口设置,并使用AtomicReference<File>作为根目录。

答案 1 :(得分:0)

将静态数据读入静态“sharedConfig”对象,该对象也有一个套接字字段 - 您可以将该字段用于侦听套接字。当acccpet()返回服务器&lt;&gt;客户端套接字,clone()'sharedConfig',推入新套接字并将该对象传递给服务器&lt;&gt;客户端工作线程。然后线程获得它可以erad甚至修改的配置的副本,如果它想要不影响任何其他线程或静态配置。