玩Java并发

最近,我需要将一些文件(每个文件都有JSON格式的对象列表(数组))转换为每个文件都具有相同数据(对象)的分隔行的文件。 这是一次性的任务,很简单。 我使用Java nio的某些功能进行了读写。 我以最简单的方式使用了GSON。 一个线程在文件上运行,转换和写入。 整个操作在几秒钟内完成。 但是,我想并发一点。 因此,我增强了可同时工作的工具。



线程数

可运行以读取文件。

阅读器线程将提交到ExecutorService。 输出是对象列表(示例中为User),将被放入BlockingQueue。

可运行以写入文件。

每个可运行对象将从阻塞队列中轮询。 它将数据行写入文件。 我没有将编写器Runnable添加到ExecutorService,而是仅使用它启动了一个线程。 Runnable具有while(some boolen is true) {...}模式。 有关以下内容的更多信息...

同步一切

BlockingQueue是这两种线程的接口。 由于writer的runnable在while循环(消费者)中运行,我希望能够使其停止,以便该工具终止。 因此,我为此使用了两个对象:

信号

读取输入文件的循环会增加一个计数器。 完成遍历输入文件并提交编写器后,我在主线程中初始化了一个信号灯: semaphore.acquire(numberOfFiles);

在每个可运行的阅读器中,我释放了信号量: semaphore.release();

原子布尔

作者的while循环使用AtomicBoolean。 只要AtomicBoolean == true,编写器将继续。 在主线程中,在获取信号量之后,我将AtomicBoolean设置为false。 这使编写器线程可以终止。

使用Java NIO

为了扫描,读取和写入文件系统,我使用了Java NIO的某些功能。

扫描: Files.newDirectoryStream(inputFilesDirectory, "*.json");
开始之前删除输出目录: Files.walkFileTree...
BufferedReader和BufferedWriter: Files.newBufferedReader(filePath); Files.newBufferedWriter(fileOutputPath, Charset.defaultCharset());

一注。 为了生成此示例的随机文件,我使用了apache commons lang: RandomStringUtils.randomAlphabetic
GitHub中的所有代码。

public class JsonArrayToJsonLines {private final static Path inputFilesDirectory = Paths.get("src\\main\\resources\\files");private final static Path outputDirectory = Paths.get("src\\main\\resources\\files\\output");private final static Gson gson = new Gson();private final BlockingQueue<EntitiesData> entitiesQueue = new LinkedBlockingQueue<>();private AtomicBoolean stillWorking = new AtomicBoolean(true);private Semaphore semaphore = new Semaphore(0);int numberOfFiles = 0;private JsonArrayToJsonLines() {}public static void main(String[] args) throws IOException, InterruptedException {new JsonArrayToJsonLines().process();}private void process() throws IOException, InterruptedException {deleteFilesInOutputDir();final ExecutorService executorService = createExecutorService();DirectoryStream<Path> directoryStream = Files.newDirectoryStream(inputFilesDirectory, "*.json");for (int i = 0; i < 2; i++) {new Thread(new JsonElementsFileWriter(stillWorking, semaphore, entitiesQueue)).start();}directoryStream.forEach(new Consumer<Path>() {@Overridepublic void accept(Path filePath) {numberOfFiles++;executorService.submit(new OriginalFileReader(filePath, entitiesQueue));}});semaphore.acquire(numberOfFiles);stillWorking.set(false);shutDownExecutor(executorService);}private void deleteFilesInOutputDir() throws IOException {Files.walkFileTree(outputDirectory, new SimpleFileVisitor<Path>() {@Overridepublic FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException {Files.delete(file);return FileVisitResult.CONTINUE;}});}private ExecutorService createExecutorService() {int numberOfCpus = Runtime.getRuntime().availableProcessors();return Executors.newFixedThreadPool(numberOfCpus);}private void shutDownExecutor(final ExecutorService executorService) {executorService.shutdown();try {if (!executorService.awaitTermination(120, TimeUnit.SECONDS)) {executorService.shutdownNow();}if (!executorService.awaitTermination(120, TimeUnit.SECONDS)) {}} catch (InterruptedException ex) {executorService.shutdownNow();Thread.currentThread().interrupt();}}private static final class OriginalFileReader implements Runnable {private final Path filePath;private final BlockingQueue<EntitiesData> entitiesQueue;private OriginalFileReader(Path filePath, BlockingQueue<EntitiesData> entitiesQueue) {this.filePath = filePath;this.entitiesQueue = entitiesQueue;}@Overridepublic void run() {Path fileName = filePath.getFileName();try {BufferedReader br = Files.newBufferedReader(filePath);User[] entities = gson.fromJson(br, User[].class);System.out.println("---> " + fileName);entitiesQueue.put(new EntitiesData(fileName.toString(), entities));} catch (IOException | InterruptedException e) {throw new RuntimeException(filePath.toString(), e);}}}private static final class JsonElementsFileWriter implements Runnable {private final BlockingQueue<EntitiesData> entitiesQueue;private final AtomicBoolean stillWorking;private final Semaphore semaphore;private JsonElementsFileWriter(AtomicBoolean stillWorking, Semaphore semaphore,BlockingQueue<EntitiesData> entitiesQueue) {this.stillWorking = stillWorking;this.semaphore = semaphore;this.entitiesQueue = entitiesQueue;}@Overridepublic void run() {while (stillWorking.get()) {try {EntitiesData data = entitiesQueue.poll(100, TimeUnit.MILLISECONDS);if (data != null) {try {String fileOutput = outputDirectory.toString() + File.separator + data.fileName;Path fileOutputPath = Paths.get(fileOutput);BufferedWriter writer = Files.newBufferedWriter(fileOutputPath, Charset.defaultCharset());for (User user : data.entities) {writer.append(gson.toJson(user));writer.newLine();}writer.flush();System.out.println("=======================================>>>>> " + data.fileName);} catch (IOException e) {throw new RuntimeException(data.fileName, e);} finally {semaphore.release();}}} catch (InterruptedException e1) {}}}}private static final class EntitiesData {private final String fileName;private final User[] entities;private EntitiesData(String fileName, User[] entities) {this.fileName = fileName;this.entities = entities;}}
}

翻译自: https://www.javacodegeeks.com/2014/12/playing-with-java-concurrency.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/361198.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

ExtJs的Reader

ExtJs的Reader Reader : 主要用于将proxy数据代理读取的数据按照不同的规则进行解析,讲解析好的数据保存到Modle中 结构图 Ext.data.reader.Reader 读取器的根类 Ext.data.reader.Json JSON格式的读取器 Ext.data.reader.Array 扩展JSON的Array读取器 Ext.data.reader.Xml XML格…

sound

sound类在 flash3.0中算是很常见的功能&#xff0c;也是很常用的&#xff0c;下面 简单的运用了 sound类&#xff0c;加载了一首歌&#xff0c;控制 播放 暂停 停止&#xff0c;和控制音量大小&#xff1b; package {import flash.display.MovieClip;import fl.controls.*;imp…

Java Lambdas和低延迟

总览 有关在Java和低延迟中使用Lambda的主要问题是&#xff1a; 它们会产生垃圾吗&#xff0c;您能做些什么吗&#xff1f; 背景 我正在开发一个支持不同有线协议的库。 这样的想法是&#xff0c;您可以描述要写入/读取的数据&#xff0c;并且有线协议确定它是否使用带有JSon或…

HTTP协议/RTSP协议/RTMP协议的区别

RTSP、 RTMP、HTTP的共同点、区别 共同点&#xff1a; 1&#xff1a;RTSP RTMP HTTP都是在应用应用层。 2&#xff1a; 理论上RTSP RTMP HTTP都可以做直播和点播&#xff0c;但一般做直播用RTSP RTMP&#xff0c;做点播用HTTP。做视频会议的时候原来用SIP协议&#xff0c;现…

2013搜狗校园招聘笔试题

研习了Linux公社发布的2013搜狗校园招聘笔试题&#xff0c;还是有些收获的。 //第一题&#xff1a;以下程序的输出是___________________ class Base { public:Base(int j):i(j){}virtual ~Base(){}void func1(){i * 10; func2();}int getValue(){return i;} protected:virtual…

Java中的线程本地存储

开发人员中鲜为人知的功能之一是线程本地存储。 这个想法很简单&#xff0c;并且在需要数据的情况下很有用。 如果我们有两个线程&#xff0c;则它们引用相同的全局变量&#xff0c;但我们希望它们具有彼此独立初始化的单独值。 大多数主要的编程语言都有该概念的实现。 例如&…

jsp中@import导入外部样式表与link链入外部样式表的区别

昨天碰到同事问了一个问题&#xff0c;impor导入外部样式与link链入外部样式的优先级是怎样的&#xff0c;为什么实验的结果是按照样式表导入后的位置来决定优先级。今天就这个问题具体总结如下&#xff1a; 先解释一下网页添加css样式的方法&#xff0c;一共有四种&#xff0c…

EBS调试

一、在请求中的调试&#xff1a; 1、用系统函数fnd_file.PUT_LINE()&#xff0c;然后在请求的查看日志中就可以看到 例如&#xff1a; fnd_file.PUT_LINE(fnd_file.log, l_customer_type); 其中l_customer_type就是要查看的变量。 2、先建一张表&#xff0c;然后在程序中执行…

Acision推出“ forgeathon” –第一个WebRTC应用挑战

Acision推出了“ forgeathon”&#xff0c;这是 面向全球开发人员的 首个在线丰富网络通信&#xff08;WebRTC&#xff09;应用挑战 加入Forgeathon&#xff0c;让Acision帮助您将应用程序或服务推向全球&#xff01; 英国雷丁– 2015年1月6 日 &#xff1a;安全&#xff0c;…

SQL Server 中的ROWID

在SQL Server中没有像Orcal中的rowid&#xff0c;但是可以运用一定的变通达到这个效果。1、建立临时表&#xff0c;其中包含rowid&#xff0c;2、重命名原表后删除临时表USE TianzxSELECT identity(int,1,1) as rowid,flow.* into temptable from flow--建立临时表&#xff0c;…

jsp中四种传递参数的方法

jsp中四种传递参数的方法如下&#xff1a; 1、form表单 2、request.setAttribute();和request.getAttribute(); 3、超链接&#xff1a;<a herf"index.jsp"?aa&bb&cc>name</a> 4、<jsp:param> 下面一一举例说明&#xff1a; 1、form表…

多个退货单

我曾经听说过&#xff0c;过去人们为使方法具有单个出口点而奋斗。 我知道这是一种过时的方法&#xff0c;从未认为它特别值得注意。 但是最近&#xff0c;我与一些仍坚持该想法的开发人员进行了联系&#xff08;最后一次是在这里 &#xff09;&#xff0c;这让我开始思考。 因…

GO 语言编程 windows 环境搭建

参考 : http://blog.csdn.net/love_se/article/details/7754274 首先是安装Go&#xff0c;这里有很详细的安装说明&#xff0c;http://code.google.com/p/golang-china/wiki/Install 或者http://golang.org/doc/install 下面我们在window下面安装&#xff0c;google有提供win安…

建立代理,而不是框架

自从引入Java注释以来&#xff0c;它已成为大型应用程序框架API的组成部分。 此类API的良好示例是Spring或Hibernate的示例&#xff0c;其中添加了几行注释代码可实现非常复杂的程序逻辑。 尽管人们可以争论这些特定API的缺点&#xff0c;但大多数开发人员都会同意&#xff0c;…

HttpServletRequest.getContextPath()取得的路径

如果项目名称为test,你在浏览器中输入请求路径&#xff1a;http://localhost:8080/test/pc/list.jsp 执行下面向行代码后打印出如下结果&#xff1a; 1、 System.out.println(request.getContextPath()); 打印结果&#xff1a;/test 2、System.out.println(request.getSer…

合理的嵌入式开发学习路线

最近网上好多新手问我&#xff0c;怎么样学习嵌入式开发&#xff1f;其实这个问题很复杂&#xff0c;因为嵌入式开发是个非常复杂的领域&#xff0c;既有深度&#xff0c;也有广度&#xff0c;是个软硬结合的领域。。。我研究的时间也不长&#xff0c;不过以后可能会研究RTOS这…

重点保护

在“ Java的一些句子 ”一文中&#xff0c;我写道&#xff1a; “受保护的方法和字段可以在同一包中的类中使用&#xff08;到目前为止与私有包相同&#xff09;&#xff0c;此外&#xff0c;还可以从其他类中使用受保护的方法和字段&#xff0c;这些类扩展了包含受保护的字段或…

机打发票打印管理

最近公司也从手写发票换成了机打发票&#xff0c;便应财务的要求做了这么一个简单的发票管理及打印系统&#xff0c;程序并不复杂。 使用C#&#xff08;2.0&#xff09; Access&#xff08;97-2003版&#xff09;/WinForm形式 系统菜单中有企业基本信息设置&#xff0c;见图4…

程序员需要了解的一点组织行为学知识

程序员由于天天和逻辑打交道&#xff0c;所以在世故的人眼里往往显得过于简单。 近来看组织行为学&#xff0c;发现其中一节列了很多特别的技能。 考虑到也许他们对程序员群体很有启示意义&#xff0c;就追加了一点说明&#xff0c;把它放在博客里。 相信这对想成为管理者的程序…

序列化的概念

讨论了为什么Optional不可序列化以及如何处理&#xff08;即将推出&#xff09;之后&#xff0c;让我们仔细看看序列化。 总览 这篇文章介绍了序列化的一些关键概念。 它尝试精简地执行此操作&#xff0c;而不会涉及太多细节&#xff0c;包括将建议降至最低。 它没有叙述&…