当前位置: 首页 > news >正文

建设网站建设网页制作0402高设计词wordpress使用置顶文章没用

建设网站建设网页制作0402高设计词,wordpress使用置顶文章没用,东莞建站网站,武进区建设局网站在以前的文章中#xff0c;我们回顾了在不同线程之间共享数据的一些主要风险#xff08;例如原子性和可见性 #xff09;以及如何设计类以安全地共享#xff08; 线程安全的设计 #xff09;。 但是#xff0c;在许多情况下#xff0c;我们将需要共享可变数据#xff0… 在以前的文章中我们回顾了在不同线程之间共享数据的一些主要风险例如原子性和可见性 以及如何设计类以安全地共享 线程安全的设计 。 但是在许多情况下我们将需要共享可变数据其中一些线程将写入而其他线程将充当读取器。 可能的情况是您只有一个域与其他域无关需要在不同线程之间共享。 在这种情况下您可以使用原子变量。 对于更复杂的情况您将需要同步。 1.咖啡店的例子 让我们从一个简单的示例开始例如CoffeeStore 。 此类开设了一家商店客户可以在此购买咖啡。 客户购买咖啡时会增加一个计数器以跟踪所售商品的数量。 商店还注册谁是最后一个来商店的客户。 public class CoffeeStore {private String lastClient;private int soldCoffees;private void someLongRunningProcess() throws InterruptedException {Thread.sleep(3000);}public void buyCoffee(String client) throws InterruptedException {someLongRunningProcess();lastClient client;soldCoffees;System.out.println(client bought some coffee);}public int countSoldCoffees() {return soldCoffees;}public String getLastClient() {return lastClient;} } 在以下程序中四个客户决定来商店购买咖啡 public static void main(String[] args) throws InterruptedException {CoffeeStore store new CoffeeStore();Thread t1 new Thread(new Client(store, Mike));Thread t2 new Thread(new Client(store, John));Thread t3 new Thread(new Client(store, Anna));Thread t4 new Thread(new Client(store, Steve));long startTime System.currentTimeMillis();t1.start();t2.start();t3.start();t4.start();t1.join();t2.join();t3.join();t4.join();long totalTime System.currentTimeMillis() - startTime;System.out.println(Sold coffee: store.countSoldCoffees());System.out.println(Last client: store.getLastClient());System.out.println(Total time: totalTime ms); }private static class Client implements Runnable {private final String name;private final CoffeeStore store;public Client(CoffeeStore store, String name) {this.store store;this.name name;}Overridepublic void run() {try {store.buyCoffee(name);} catch (InterruptedException e) {System.out.println(interrupted sale);}} } 主线程将使用Thread.join等待所有四个客户端线程完成。 一旦客户离开我们显然应该算出我们商店中售出的四种咖啡但是您可能会得到与上面的类似的意外结果 Mike bought some coffee Steve bought some coffee Anna bought some coffee John bought some coffee Sold coffee: 3 Last client: Anna Total time: 3001 ms 我们丢了一杯咖啡最后一位客户John也不是那一位Anna。 原因是由于我们的代码未同步因此线程交错。 我们的buyCoffee操作应设为原子操作。 2.同步如何工作 同步块是由锁保护的代码区域。 当线程进入同步块时它需要获取其锁并且一旦获取它就不会释放它直到退出该块或引发异常。 这样当另一个线程尝试进入同步块时只有所有者线程释放它后它才能获取其锁。 这是Java机制可确保仅在给定时间在线程上执行同步的代码块从而确保该块内所有动作的原子性。 好的所以您使用锁来保护同步块但是什么是锁 答案是任何Java对象都可以用作锁称为内在锁。 现在我们将看到使用同步时这些锁的一些示例。 3.同步方法 同步方法由两种类型的锁保护 同步实例方法 隐式锁定为“ this”这是用于调用该方法的对象。 此类的每个实例将使用自己的锁。 同步静态方法 锁是Class对象。 此类的所有实例将使用相同的锁。 像往常一样用一些代码可以更好地看到这一点。 首先我们将同步一个实例方法。 它的工作方式如下我们有两个线程线程1和线程2共享该类的一个实例而另一个线程线程3使用了另一个实例 public class InstanceMethodExample {private static long startTime;public void start() throws InterruptedException {doSomeTask();}public synchronized void doSomeTask() throws InterruptedException {long currentTime System.currentTimeMillis() - startTime;System.out.println(Thread.currentThread().getName() | Entering method. Current Time: currentTime ms);Thread.sleep(3000);System.out.println(Thread.currentThread().getName() | Exiting method);}public static void main(String[] args) {InstanceMethodExample instance1 new InstanceMethodExample();Thread t1 new Thread(new Worker(instance1), Thread-1);Thread t2 new Thread(new Worker(instance1), Thread-2);Thread t3 new Thread(new Worker(new InstanceMethodExample()), Thread-3);startTime System.currentTimeMillis();t1.start();t2.start();t3.start();}private static class Worker implements Runnable {private final InstanceMethodExample instance;public Worker(InstanceMethodExample instance) {this.instance instance;}Overridepublic void run() {try {instance.start();} catch (InterruptedException e) {System.out.println(Thread.currentThread().getName() interrupted);}}} } 由于doSomeTask方法是同步的因此您希望在给定的时间只有一个线程将执行其代码。 但这是错误的因为它是一个实例方法。 不同的实例将使用不同的锁如输出所示 Thread-1 | Entering method. Current Time: 0 ms Thread-3 | Entering method. Current Time: 1 ms Thread-3 | Exiting method Thread-1 | Exiting method Thread-2 | Entering method. Current Time: 3001 ms Thread-2 | Exiting method 由于线程1和线程3使用不同的实例因此使用了不同的锁因此它们都同时进入该块。 另一方面线程2使用与线程1相同的实例和锁。 因此它必须等到线程1释放锁。 现在让我们更改方法签名并使用静态方法。 除以下行外 StaticMethodExample具有相同的代码 public static synchronized void doSomeTask() throws InterruptedException { 如果执行main方法将得到以下输出 Thread-1 | Entering method. Current Time: 0 ms Thread-1 | Exiting method Thread-3 | Entering method. Current Time: 3001 ms Thread-3 | Exiting method Thread-2 | Entering method. Current Time: 6001 ms Thread-2 | Exiting method 由于同步方法是静态的因此它由Class对象锁保护。 尽管使用了不同的实例所有线程仍需要获取相同的锁。 因此任何线程都必须等待上一个线程释放锁。 4.回到咖啡店的例子 我现在修改了Coffee Store示例以使其方法同步。 结果如下 public class SynchronizedCoffeeStore {private String lastClient;private int soldCoffees;private void someLongRunningProcess() throws InterruptedException {Thread.sleep(3000);}public synchronized void buyCoffee(String client) throws InterruptedException {someLongRunningProcess();lastClient client;soldCoffees;System.out.println(client bought some coffee);}public synchronized int countSoldCoffees() {return soldCoffees;}public synchronized String getLastClient() {return lastClient;} } 现在如果我们执行该程序我们将不会失去任何销售 Mike bought some coffee Steve bought some coffee Anna bought some coffee John bought some coffee Sold coffee: 4 Last client: John Total time: 12005 ms 完善 好吧真的是吗 现在程序的执行时间为12秒。 您肯定已经注意到在每次销售期间都会执行someLongRunningProcess方法。 它可以是与销售无关的操作但是由于我们同步了整个方法所以现在每个线程都必须等待它执行。 我们可以将这段代码放在同步块之外吗 当然 下一节将介绍同步块。 5.同步块 上一节向我们展示了我们可能并不总是需要同步整个方法。 由于所有同步代码都强制对所有线程执行进行序列化因此我们应最小化同步块的长度。 在我们的咖啡店示例中我们可以省去长时间运行的过程。 在本节的示例中我们将使用同步块 在SynchronizedBlockCoffeeStore中 我们修改buyCoffee方法以将长时间运行的进程排除在同步块之外 public void buyCoffee(String client) throws InterruptedException {someLongRunningProcess();synchronized(this) {lastClient client;soldCoffees;System.out.println(client bought some coffee);} }public synchronized int countSoldCoffees() {return soldCoffees;}public synchronized String getLastClient() {return lastClient;} 在上一个同步块中我们将“ this”用作其锁。 它与同步实例方法中的锁相同。 当心使用另一个锁因为我们正在此类的其他方法 countSoldCoffees和getLastClient 中使用此锁。 让我们看看执行修改后的程序的结果 Mike bought some coffee John bought some coffee Anna bought some coffee Steve bought some coffee Sold coffee: 4 Last client: Steve Total time: 3015 ms 在保持代码同步的同时我们大大减少了程序的时间。 6.使用私人锁 上一节对实例对象使用了锁定但是您可以将任何对象用作其锁定。 在本节中我们将使用私人锁看看使用私人锁会有什么风险。 在PrivateLockExample中 我们有一个由私有锁myLock保护的同步块 public class PrivateLockExample {private Object myLock new Object();public void executeTask() throws InterruptedException {synchronized(myLock) {System.out.println(executeTask - Entering...);Thread.sleep(3000);System.out.println(executeTask - Exiting...);}} } 如果一个线程进入executeTask方法将获取myLock锁。 在由相同的myLock锁保护的此类中进入其他方法的任何其他线程都必须等待才能获取它。 但是现在让我们想象一下有人想要扩展此类以添加自己的方法并且由于需要使用相同的共享数据因此这些方法也需要同步。 由于该锁在基类中是私有的因此扩展类将无法访问它。 如果扩展类同步其方法则将通过“ this”进行保护。 换句话说它将使用另一个锁。 MyPrivateLockExample扩展了上一个类并添加了自己的同步方法executeAnotherTask public class MyPrivateLockExample extends PrivateLockExample {public synchronized void executeAnotherTask() throws InterruptedException {System.out.println(executeAnotherTask - Entering...);Thread.sleep(3000);System.out.println(executeAnotherTask - Exiting...);}public static void main(String[] args) {MyPrivateLockExample privateLock new MyPrivateLockExample();Thread t1 new Thread(new Worker1(privateLock));Thread t2 new Thread(new Worker2(privateLock));t1.start();t2.start();}private static class Worker1 implements Runnable {private final MyPrivateLockExample privateLock;public Worker1(MyPrivateLockExample privateLock) {this.privateLock privateLock;}Overridepublic void run() {try {privateLock.executeTask();} catch (InterruptedException e) {e.printStackTrace();}}}private static class Worker2 implements Runnable {private final MyPrivateLockExample privateLock;public Worker2(MyPrivateLockExample privateLock) {this.privateLock privateLock;}Overridepublic void run() {try {privateLock.executeAnotherTask();} catch (InterruptedException e) {e.printStackTrace();}}} } 该程序使用两个工作线程分别执行executeTask和executeAnotherTask 。 输出显示线程如何交错因为它们没有使用相同的锁 executeTask - Entering... executeAnotherTask - Entering... executeAnotherTask - Exiting... executeTask - Exiting...7.结论 我们已经使用Java的内置锁定机制回顾了内部锁定的使用。 这里的主要关注点是需要使用共享数据的同步块。 必须使用相同的锁。 这篇文章是Java Concurrency Tutorial系列的一部分。 检查此处以阅读本教程的其余部分。 您可以在Github上找到源代码。 翻译自: https://www.javacodegeeks.com/2014/09/java-concurrency-tutorial-locking-intrinsic-locks.html
http://www.pierceye.com/news/601423/

相关文章:

  • 淮北市重点工程建设局网站重庆哪家网站
  • 音乐网站开发背景及意义自定义建设网站
  • 商标设计网站猪八戒宝塔一键wordpress
  • 公司网站用什么开发网站 建设 计划书
  • 安陆市城乡建设局网站w10怎么做信任网站
  • wordpress上站工具内网门户网站
  • 商城网站服务器漳浦建设银行网站
  • 可视化 网站开发工具音乐网站后台管理模板
  • 网站架构功能模块及描述网站聊天怎么做
  • 京东电子商务网站的建设做网站运营需要什么资源
  • 市北建筑建网站哪家好个体户可以做网站吗
  • 怎么建自己的网站?网站优化包括哪些内容
  • 网站后台登录域名国外网站网站app
  • 山西建设工程协会网站wordpress二次元主题个人
  • 加强人社局网站建设获取小程序api
  • 服务器网站备案学生ppt模板免费下载 素材
  • 手机做网站软件运营管理培训
  • 迅博威网站建设南宁 建网站 公司
  • 河北省建设机械协会是正规网站吗网站及网页设计费用
  • 门户网站seo前期铁岭网站建设移动网站
  • 肇庆免费模板建站jsp电商网站开发流程图
  • 阿里巴巴国际站网站建设青岛网站搭建公司哪家好
  • 能看人与动物做的网站浙江企业响应式网站建设设计
  • 乌兰察布做网站公司营销策划公司有哪些职位
  • 南宁区建设银行招聘网站建设部网站申请表无法打印
  • 建一个网站怎么赚钱吗家具网站源码
  • 云优化网站建设wordpress开启icon
  • 招聘网站开发的目的与意义农特产品电商网站建设目标
  • 三水 网站建设公司企业黄页
  • 网站建设公司词辽宁阜新建设学校官方网站