首页 文章 精选 留言 我的

精选列表

搜索[并发编程],共10000篇文章
优秀的个人博客,低调大师

ZooKeeper客户端编程(三)

前面说了一些ZooKeeper理论上的内容,对于实践部分,想必都是跃跃欲试。这里我想主要介绍几个Java的demo来起到抛砖引玉的作用,Zookeeper客户端框架具体的细节部分若深入起来不是三言两语能解释的完的,我适当的说明一些,深入的研究还望一起努力。 图与文无关 假设你已经对zkCli的基本命令较熟悉了: create 创建节点 delete 删除节点 exists 判断节点是否存在 getChildren 获取节点下的所有子节点 getData 获取节点的数据 setData 在节点写入或更新数据 getACL 获取某节点的ACL setACL 设置某节点的ACL sync 同步某客户端znode的状态 准备 电脑上有Java开发环境 maven,下载ZooKeeper Java客户端的源码 浏览器 ,ZooKeeper API文档(http://zookeeper.apache.org/doc/r3.4.6/api/index.html) Java案例 列出指定节点下的内容 public class ZooState { public static void main(String[] args) throws IOException, KeeperException, InterruptedException { String hostPort = "192.168.8.250:2181"; String zPath = "/"; List<String> zooChildren = new ArrayList<>(); //构造ZooKeeper的实例 ZooKeeper zooKeeper = new ZooKeeper(hostPort, 2000, null); try { //获取节点下的内容 zooChildren = zooKeeper.getChildren(zPath,false); System.out.println("Znodes of /:"); for (String zooChild : zooChildren) { System.out.println(zooChild); } } catch (InterruptedException e) { e.printStackTrace(); } catch (KeeperException e) { e.printStackTrace(); } } } ZooKeeper的构造参数: connectString 服务器列表,多个服务器用逗号分隔开,如"127.0.0.1:3000,127.0.0.1:3001,127.0.0.1:3002"。如果要使用chroot特性,那么加上路径后缀。如"127.0.0.1:3000,127.0.0.1:3001,127.0.0.1:3002/app/a" sessionTimeout session的超时时间,毫秒为单位。在sessionTimeout内没有心跳检测,会话就标记为失效的 watcher watcher对象用来通知对象的改变,可以传入null canBeReadOnly 是否支持只读模式。当ZooKeeper服务器挂掉的时候,还是希望ZooKeeper能提供读服务。 sessionId和sessionPasswd 用于确定唯一一个会话,可以实现客户端的会话复用 Zookeeper实例提供了很多我们操作ZooKeeper数据的接口,记得看它的详细介绍。 ZooKeeper实例图 我自己是觉得Java Doc已经解释的很详细了,我列出几个使用客户端API的案例。 注册zNode监听事件 @Slf4j public class DataWatch implements Watcher,Runnable{ String hostPart = "192.168.8.250:2181"; String zooDataPath = "/MyConfig"; byte[] zooData = null; ZooKeeper zk; public static void main(String[] args) throws IOException, KeeperException, InterruptedException { DataWatch dataWatch = new DataWatch(); dataWatch.printData(); dataWatch.run(); } public DataWatch() { try { zk = new ZooKeeper(hostPart,2000,this); if (zk.exists(zooDataPath,this) == null){ zk.create(zooDataPath,"".getBytes(), ZooDefs.Ids.OPEN_ACL_UNSAFE,CreateMode.PERSISTENT); } } catch (IOException | KeeperException | InterruptedException e) { e.printStackTrace(); } } public void printData() throws KeeperException, InterruptedException { zooData = zk.getData(zooDataPath,this,null); String zString = new String(zooData); log.info("\nCurrent Data: %s %s",zooDataPath,zString); } @Override public void run() { try { synchronized (this){ while (true){ wait(); } } } catch (InterruptedException e) { e.printStackTrace(); Thread.currentThread().interrupt(); } } @Override public void process(WatchedEvent event) { System.out.printf("\nReceive Events: %s",event.toString()); // 我们只处理数据改变的Node if (event.getType() == Event.EventType.NodeDataChanged){ try { printData(); } catch (KeeperException | InterruptedException e) { e.printStackTrace(); } } } } 简单的实现将监听器指向自己,当节点数据改变的时候打印节点中的内容。在zkCli中试着改变/MyConfig节点查看效果。 ACL访问控制的例子 public class ZooAcl { public static void main(String[] args) throws IOException, KeeperException, InterruptedException { String hostPort = "192.168.8.250:2181"; String zooDataPath = "/Auth"; byte[] zooData = null; ZooKeeper zk = new ZooKeeper(hostPort, 2000, null); zk.addAuthInfo("digest","foo:true".getBytes()); zk.create(zooDataPath, "init".getBytes(), ZooDefs.Ids.CREATOR_ALL_ACL, CreateMode.EPHEMERAL); ZooKeeper zk2 = new ZooKeeper(hostPort, 2000, null); zk2.getData(zooDataPath,false,null); } } 这个实例,首先创建一个包含权限信息的客户端创建一个数据节点,然后使用另外一个不包含权限信息的客户端访问。运行会出现异常。 Exception in thread "main" org.apache.zookeeper.KeeperException$NoAuthException: KeeperErrorCode = NoAuth for /Auth 额外-Curator 除了ZooKeeper官方的Java API,开源社区也提供了更好的对ZooKeeper的封装,常用的有ZkClient和Curator。最受欢迎的是Curator,所以建议使用Curator,若想要对ZooKeeper有更深入的研究,两者的实现都可以看一下。 我这里略提一些Curator的内容。它是Netfix公司开源的一套ZooKeeper客户端框架,它解决了很多ZooKeeper客户端非常底层的细节开发工作,包括连接重连,反复注册Watcher和NodeExistsException异常等。目前是Apache的顶级项目,ZooKeeper的核心代码提交者Patrick Hunt以一句“Guava is to Java what Curator to ZooKeeper”。对其进行了高度评价。 因为Curator对底层封装的很好,用起来也特别方便,并且提供了一套易用性和可读性更强的Fluent风格的客户端API框架。 Curator有些maven的源值得提一下: <!-- https://mvnrepository.com/artifact/org.apache.curator/curator-framework --> // 开发所用的curator maven依赖 <dependency> <groupId>org.apache.curator</groupId> <artifactId>curator-framework</artifactId> <version>4.0.1</version> </dependency> <!-- https://mvnrepository.com/artifact/org.apache.curator/curator-examples --> // curator的使用案例。可以进行参考 <dependency> <groupId>org.apache.curator</groupId> <artifactId>curator-examples</artifactId> <version>4.0.1</version> </dependency> <!-- https://mvnrepository.com/artifact/org.apache.curator/curator-recipes --> // Curator的常见用法,常用的应用场景 <dependency> <groupId>org.apache.curator</groupId> <artifactId>curator-recipes</artifactId> <version>4.0.1</version> </dependency> // 几句样例代码 CuratorFramework client = CuratorFrameworkFactory.builder() .connectString("192.168.8.250:2181") .sessionTimeoutMs(5000) .retryPolicy(new ExponentBackoffRetry(1000,3)) .build(); client.start(); //创建一个节点,初始内容为空 client.create().forPath("/parent"); //创建一个节点,附带初始内容 client.create().forPath("/parent","init".getBytes()); // 创建一个临时节点,初始内容为空 client.create().withMode( CreateMode.EPHEMERAL ).forPath("/parent"); // 创建一个临时节点,并自动创建父节点,这个接口非常有用,开发人员经常碰到NoNodeException. client.create() .creatingParentsIfNeeded() .withMode( CreateMode.EPHEMERAL ).forPath("/parent"); 最后 这篇文章主要给了几个关于ZooKeeper Java API的用法,API中有很多常用的用法文档写的很明白了,就未过多的进行讲解。最后又提了一下使用很广泛的Curator框架,带大家了解了一下Curator的用法,想要继续深入的话全屏个人兴趣。 参考 《从Paxos到ZooKeeper-分布式一致性原理与实践》 《Apache ZooKeeper Essential》 ZooKeeper Programing Guide Curator 官网

优秀的个人博客,低调大师

android网络编程——HttpGet、HttpPost比较

在Android SDK中提供了Apache HttpClient(org.apache.http.*)模块。在这个模块中涉及到两个重要的类:HttpGet和HttpPost,他们有共性也有不同。 HttpGet和HttpPost创建方式相同: 1、创建HttpGet(或HttpPost)对象,将要请求的URL通过构造方法传入HttpGet(或HttpPost)对象中; 2、使用DefaultHttpClient类的execute方法发送HTTP GET或HTTP POST 请求,并返回HttpResponse对象; 3、通过HttpResponse接口的getEntity方法返回响应信息。 HttpGet和HttpPost不同点,HttpPost在使用是需要传递参数 ,使用List<NameValuePair>添加参数。 List<NameValuePair> postParameters = new ArrayList<NameValuePair>(); postParameters.add(new BasicNameValuePair("username", "test")); postParameters.add(new BasicNameValuePair("password", "test1234")); /** * @author 张兴业 * 邮箱:xy-zhang#163.com * android开发进阶群:278401545 * */ 本文转自xyz_lmn51CTO博客,原文链接: http://blog.51cto.com/xyzlmn/1230790 ,如需转载请自行联系原作者

优秀的个人博客,低调大师

Cocoa编程学习笔记之MVC

Cocoa 使用了一种修改版本的MVC模式来处理GUI的显示。MVC模式(自1979年以来)已经出现很长时间了,它皆在分离显示用户界面所需的大量任务,并处理用户交互。正如名称所蕴含的,MVC具有三个主要部分,Model(模型)、View(视图)和Controller(控制器): 模型——模型是特定于领域的数据表现形式。比如说,我们正在创建一个任务列表应用程序。你可能会有一个Task对象的集合,书写为List。 你或许把这些数据保存在数据库、XML文件,或者甚至从Web Service中得到,不过MVC不那么关心它们是在何处/如何来持久保存的(乃至它们是什么)。相反,它特别专注于如何显示这些数据,并处理与用户交互的,好的模型类不包括任何有关用户界面的内容,可以在多个应用程序中使用。视图——视图代表了数据如何实际地显示出来。在我们这个假设的任务应用程序中,会在一个网页(以HTML的方式)中来显示这些任务,也会在一个WPF页面中(以XAML的方式)来显示,或者在一个iPhone应用程序中显示为UITableView 。如果用户点击某个任务,要删除之,那么视图通常会触发一个事件,或对Controller(控制器)进行一个回调,好的视图类是通用类,可以在多个应用中使用。控制器——控制器是模型和视图间的粘合剂,负责控制整个应用的流程。控制器的目的就是获取模型中的数据,告知视图来显示。控制器还侦听着视图的事件,在用户选中一个任务来删除的时候,控制着任务从模型中删除。通过分离显示数据、持久化数据和处理用户交互的职责,MVC模式有助于创建易于理解的代码。而且,它促进了视图和模型的解耦,以便模型能被重用。例如,在你的应用程序中,有两个界面,基于Web的和WPF的,那么你可以在两者中都使用同样的模型定义代码。 因而,在很多MVC框架中不管具体的工作方式如何,基本原理都大致如此的。然而,在Cocoa(及Cocoa Touch)中,还是或多或少有所不同,苹果用MVC来代表Views(视图)、View Controller(视图控制器)和Models(模型);但是在不同的控件中,它们却不是完全一致的,实现的方式也不太一样。 在Objective-C/Cocoa的世界里,我们建立的controller通常是指应用程序(Application)的委托(Delegate),或者可以简单称做app delegate。当你在Objective-C里面建立一个app delegate的时候,这个delegate可以做为你所有model和view的controller,或者你也可以为不同的model和view分别创建controller。 本文来自云栖社区合作伙伴“doNET跨平台”,了解相关信息可以关注“opendotnet”微信公众号

优秀的个人博客,低调大师

Linux之shell编程函数使用

linux shell 可以用户定义函数,然后在shell脚本中可以随便调用。下面说说它的定义方法,以及调用需要注意那些事项。 原文和作者一起讨论:http://www.cnblogs.com/intsmaze/p/6675421.html 微信:intsmaze 函数定义 #!/bin/sh # func1.sh hello() ## 函数定义 { echo "Hello there today's date is `date +%Y-%m-%d`" # return 2 ###返回值其实是状态码,只能在[0-255]范围内 } hello #函数调用 echo $? #获取函数的return值,就是获取上一个命令的状态码,如果return 2没有注释,就是获取return 2 命令的状态吗。 echo "now going to the function hello intsmaze" 调用脚本 [hadoop@centos-Reall-131 shtest]$ sh func1.sh Hello there today's date is 2017-04-06 0 now going to the function hello intsmaze 注意: 1.必须在调用函数之前,先声明函数,shell脚本是逐行运行。不会像其它语言一样先预编译。 2.函数返回值,只能通过$? 系统变量获得,可以显示加:return 返回,如果不加,将以最后一条命令运行结果,作为返回值。 return后跟数值n(0-255) 函数参数 #!/bin/bash # fun1.sh funWithParam(){ echo "第一个参数为 $1 !" echo "第二个参数为 $2 !" echo "第十个参数为 $10 !" echo "第十个参数为 ${10} !" echo "第十一个参数为 ${11} !" echo "参数总数有 $# 个!" echo "作为一个字符串输出所有参数 $* !" } funWithParam 1 2 3 4 5 6 7 8 9 34 73 注意,$10 不能获取第十个参数,获取第十个参数需要${10}。当n>=10时,需要使用${n}来获取参数。 [hadoop@centos-Reall-131 shtest]$ sh fun1.sh 第一个参数为 1 ! 第二个参数为 2 ! 第十个参数为 10 ! 第十个参数为 34 ! 第十一个参数为 73 ! 参数总数有 11 个! 作为一个字符串输出所有参数 1 2 3 4 5 6 7 8 9 34 73 ! 函数返回值 #!/bin/bash # fun2.sh funWithReturn(){ echo "这个函数会对输入的两个数字进行相加运算..." echo "输入第一个数字: " read aNum echo "输入第二个数字: " read anotherNum echo "两个数字分别为 $aNum 和 $anotherNum !" return $(($aNum+$anotherNum)) } funWithReturn echo "输入的两个数字之和为 $? !"#这里上一个命令是 return $(($aNum+$anotherNum)) 调用脚本 [hadoop@centos-Reall-131 shtest]$ sh fun2.sh 这个函数会对输入的两个数字进行相加运算... 输入第一个数字: 100 输入第二个数字: 200 两个数字分别为 100 和 200 ! 输入的两个数字之和为 44 !#这里上一个命令是 return 300 跨脚本调用函数 假如上述的脚本文件fun1.sh保存在此路径:/root/fun1.sh 则可在脚本fun_other.sh中调用脚本fun1.sh中的函数 #!/bin/bash # fun_other.sh . /root/fun1.sh # 注: . 和 / 之间有空格 # 或者 source /root/fun1.sh funWithParam 11 22 33 44 55 66 77 88 99 100 101 调用脚本 [hadoop@centos-Reall-131 shtest]$ sh fun_other.sh 第一个参数为 1 ! 第二个参数为 2 ! 第十个参数为 10 ! 第十个参数为 34 ! 第十一个参数为 73 ! 参数总数有 11 个! 作为一个字符串输出所有参数 1 2 3 4 5 6 7 8 9 34 73 ! 第一个参数为 11 ! 第二个参数为 22 ! 第十个参数为 110 ! 第十个参数为 100 ! 第十一个参数为 101 ! 参数总数有 11 个! 作为一个字符串输出所有参数 11 22 33 44 55 66 77 88 99 100 101 ! 作者: intsmaze(刘洋) 出处: http://www.cnblogs.com/intsmaze/ 老铁,你的--->推荐,--->关注,--->评论--->是我继续写作的动力。 微信公众号号:Apache技术研究院 由于博主能力有限,文中可能存在描述不正确,欢迎指正、补充! 本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。

优秀的个人博客,低调大师

C++异步编程最佳实践

Mapreduce问题 多个数据,进行同类型计算,最后汇总结果,怎样用C++解锁此类问题? 这个最简单了,单线程循环处理每份数据好了。这有何难,创建一块地方,针对每份数据创建个线程执行计算,将结果写入先前创建的数据的对应地方,等各线程结束,完活。 上面的说法都对,只是不够好。对于单线程处理,在这个多核时代,未免大马拉小车,有点浪费CPU。当问题规模变大,你准备花多长时间计算。对于多线程这个说法,从策略上来说,没有问题。但问题是你不得不手动启动线程,把结果放到共享内存里,通过thread.join()等待结束。这点操作难度,对于我大C++开发来说算啥,分分钟就搞定了。但问题又来了,现在你的老板问你要针对单份数据的处理函数,返回结果。呵呵,原来的单份数据处理函数,十有八九长成这样: RetType deal(Indata t,Retdata&

资源下载

更多资源
Nacos

Nacos

Nacos /nɑ:kəʊs/ 是 Dynamic Naming and Configuration Service 的首字母简称,一个易于构建 AI Agent 应用的动态服务发现、配置管理和AI智能体管理平台。Nacos 致力于帮助您发现、配置和管理微服务及AI智能体应用。Nacos 提供了一组简单易用的特性集,帮助您快速实现动态服务发现、服务配置、服务元数据、流量管理。Nacos 帮助您更敏捷和容易地构建、交付和管理微服务平台。

Spring

Spring

Spring框架(Spring Framework)是由Rod Johnson于2002年提出的开源Java企业级应用框架,旨在通过使用JavaBean替代传统EJB实现方式降低企业级编程开发的复杂性。该框架基于简单性、可测试性和松耦合性设计理念,提供核心容器、应用上下文、数据访问集成等模块,支持整合Hibernate、Struts等第三方框架,其适用范围不仅限于服务器端开发,绝大多数Java应用均可从中受益。

Rocky Linux

Rocky Linux

Rocky Linux(中文名:洛基)是由Gregory Kurtzer于2020年12月发起的企业级Linux发行版,作为CentOS稳定版停止维护后与RHEL(Red Hat Enterprise Linux)完全兼容的开源替代方案,由社区拥有并管理,支持x86_64、aarch64等架构。其通过重新编译RHEL源代码提供长期稳定性,采用模块化包装和SELinux安全架构,默认包含GNOME桌面环境及XFS文件系统,支持十年生命周期更新。

WebStorm

WebStorm

WebStorm 是jetbrains公司旗下一款JavaScript 开发工具。目前已经被广大中国JS开发者誉为“Web前端开发神器”、“最强大的HTML5编辑器”、“最智能的JavaScript IDE”等。与IntelliJ IDEA同源,继承了IntelliJ IDEA强大的JS部分的功能。

用户登录
用户注册