1 00:00:00,360 --> 00:00:04,440 Welcome to Workbook eleven point six, the main focus of this workbook is going to be thread safety 2 00:00:04,440 --> 00:00:06,060 and locking critical parts of our code. 3 00:00:06,570 --> 00:00:11,640 And so the first thing we're gonna do is define a function whose document I'm going to copy right now. 4 00:00:12,990 --> 00:00:13,830 Copied over. 5 00:00:15,380 --> 00:00:19,430 And the function seems to be void, so we'll say public static void. 6 00:00:22,100 --> 00:00:26,600 It's called increments, and it expects a string parameter called file. 7 00:00:28,680 --> 00:00:32,729 And now inside the function or in a run through every single line inside the file and from learning 8 00:00:32,729 --> 00:00:35,610 the part, I left you a line of code to obtain the path. 9 00:00:36,830 --> 00:00:38,510 We're going to have to make some imports. 10 00:00:43,990 --> 00:00:45,370 And this throws an exception. 11 00:00:45,400 --> 00:00:49,030 Uri syntax exceptions, so from here in a try to run the code. 12 00:00:53,160 --> 00:00:59,190 And catch the exception if the cartels catch your eye syntax exception. 13 00:01:00,800 --> 00:01:04,459 And print the message that the exception comes with in case of a failure. 14 00:01:05,560 --> 00:01:10,180 Now we're going to use the file class to read every single line in the file path as a stream, so we'll 15 00:01:10,180 --> 00:01:10,960 see files. 16 00:01:13,100 --> 00:01:15,920 The lines will pass in the path. 17 00:01:16,190 --> 00:01:21,710 And now we can run through every single line inside of whatever file we're passing in as a stream of 18 00:01:21,710 --> 00:01:22,430 elements. 19 00:01:23,690 --> 00:01:28,340 And so the first operation is to map every single element to a quantity value, but if you look at the 20 00:01:28,340 --> 00:01:32,060 first row, it's just a bunch of column headers that we need to skip. 21 00:01:32,420 --> 00:01:37,370 So the first operation actually has to be the skip the first line. 22 00:01:38,670 --> 00:01:43,260 And then what we need to do is map every element to a quantity value. 23 00:01:43,790 --> 00:01:49,950 So will map to ENT because quantity is an integer. 24 00:01:52,510 --> 00:01:55,960 Here we receive every single element in the stream as a line string. 25 00:01:57,410 --> 00:02:02,300 And here what we need to do is split the string around the comma separator, what that's going to do 26 00:02:02,300 --> 00:02:05,120 is return an array of three string values. 27 00:02:05,420 --> 00:02:07,520 We knew that Index two was an integer value. 28 00:02:07,530 --> 00:02:08,389 So what we're going to do? 29 00:02:09,560 --> 00:02:14,570 Is return index to and from the string value, we're going to say INT? 30 00:02:15,710 --> 00:02:17,900 Or integer, I should say that percent. 31 00:02:19,640 --> 00:02:22,000 Pass an integer out of the following string value. 32 00:02:25,240 --> 00:02:30,250 OK, so at this point in the pipeline, every single element in the stream was mapped to a quantity. 33 00:02:30,640 --> 00:02:33,100 And now we're going to run through every single quantity. 34 00:02:33,110 --> 00:02:34,840 This is going to be our terminal operation. 35 00:02:35,620 --> 00:02:38,080 This terminal operation in this case, returns void. 36 00:02:39,130 --> 00:02:44,620 It's going to run through every single quantity and every time we run through an element inside the 37 00:02:44,620 --> 00:02:48,400 stream, what we're going to do is increment the sample size. 38 00:02:48,400 --> 00:02:52,300 So here we'll say sample size plus plus. 39 00:02:53,700 --> 00:02:57,390 And quantity plus equals quantity. 40 00:03:05,560 --> 00:03:11,080 Seems there's an exception we have to catch, and it is the i o exception catch. 41 00:03:12,070 --> 00:03:13,600 I know exception. 42 00:03:21,200 --> 00:03:26,540 And so now what we need to do is call this function first HSV one, two and three, so we're enough 43 00:03:26,540 --> 00:03:28,700 to call this three different times. 44 00:03:29,120 --> 00:03:35,990 We're going to assume this should run in the background because every year we file as about 500000 records. 45 00:03:39,850 --> 00:03:41,200 So back here, what I'm going to do. 46 00:03:42,350 --> 00:03:44,000 Is it going to create a threat pool? 47 00:03:46,520 --> 00:03:51,050 Oh, you know what, we should probably highlight this and bring it back a little so you can press shift 48 00:03:51,050 --> 00:03:51,800 and tab. 49 00:03:52,930 --> 00:03:53,560 This should be good. 50 00:03:54,730 --> 00:03:55,130 OK. 51 00:03:55,540 --> 00:03:58,510 And now what I'm going to do is create a threat pool. 52 00:03:59,710 --> 00:04:01,810 Secular service, secular. 53 00:04:04,220 --> 00:04:09,130 And I don't know why the inventing is out, there should be at least four spaces one two three four. 54 00:04:09,680 --> 00:04:12,280 OK is equal to executor's. 55 00:04:13,880 --> 00:04:19,040 New fixed threat pool, and since we're just performing three tasks, we'll just have three threads. 56 00:04:21,399 --> 00:04:24,670 And now what we can say is executor that submit. 57 00:04:25,930 --> 00:04:27,550 And we're going to submit. 58 00:04:28,700 --> 00:04:34,070 Oh, you know what, it seems like it's better to just run through this array of files. 59 00:04:34,610 --> 00:04:35,630 So for. 60 00:04:36,840 --> 00:04:39,870 I is smaller than files that length. 61 00:04:40,980 --> 00:04:42,330 We're going to say executor. 62 00:04:43,210 --> 00:04:47,620 Does submit here will call the runnable task increment. 63 00:04:49,270 --> 00:04:52,630 And to it, we're going to pass and files an index I. 64 00:04:54,860 --> 00:04:57,290 We seem to be getting an error, and you know what? 65 00:04:57,440 --> 00:05:02,450 Instead of using a for loop that relies on a counter, we'll just use the for each loop. 66 00:05:03,230 --> 00:05:05,990 We'll run through every single string inside of the files array. 67 00:05:06,740 --> 00:05:08,840 And here we'll say executor does submit. 68 00:05:10,030 --> 00:05:11,860 And submit our runnable task. 69 00:05:22,830 --> 00:05:29,010 OK, and as we submit every single task, they're going to automatically run in the background and we 70 00:05:29,010 --> 00:05:33,570 need to make sure that all tasks have been completed before we display the information to the user. 71 00:05:34,290 --> 00:05:40,870 So what I'm going to do is create a countdown match countdown that's large is equal to a new countdown 72 00:05:40,870 --> 00:05:41,370 clock. 73 00:05:42,520 --> 00:05:44,020 That counts down from three. 74 00:05:45,780 --> 00:05:48,960 And to our increment function. 75 00:05:50,010 --> 00:05:51,390 I'm going to pass any latch. 76 00:06:05,550 --> 00:06:08,970 And at the end of every task, we're going to say large dark countdown. 77 00:06:13,070 --> 00:06:16,310 And then right here, if we say a large Typekit await. 78 00:06:17,370 --> 00:06:23,610 This latch is going to stay closed until it counts down to zero, which in this case until every single 79 00:06:23,610 --> 00:06:25,050 task has been executed. 80 00:06:25,830 --> 00:06:28,620 And to right here we can safely present the data to the user. 81 00:06:28,900 --> 00:06:30,240 You can say sample size. 82 00:06:31,710 --> 00:06:33,890 And reference the sample size. 83 00:06:40,420 --> 00:06:42,460 You can also say quantity sold. 84 00:06:52,480 --> 00:06:54,850 In reference, the quantity sold. 85 00:06:56,930 --> 00:06:59,810 If everything works correctly, we should be getting the following values. 86 00:07:04,270 --> 00:07:05,680 I'll keep them to for now. 87 00:07:07,030 --> 00:07:14,650 We'll run the application, oh, don't forget, actually shut down the executor service. 88 00:07:17,730 --> 00:07:18,030 OK. 89 00:07:27,120 --> 00:07:28,560 And this is not good. 90 00:07:28,920 --> 00:07:31,450 Also, another thing quantity sold is zero. 91 00:07:31,470 --> 00:07:35,860 That's oh the variable here should be quantity sold, not quantity. 92 00:07:35,880 --> 00:07:37,290 That makes more sense. 93 00:07:37,680 --> 00:07:38,880 We'll just rerun it. 94 00:07:43,180 --> 00:07:44,170 Yeah, that's not good at all. 95 00:07:44,860 --> 00:07:49,780 The correct values are the following, and you'd be wondering why the values aren't correct, and once 96 00:07:49,780 --> 00:07:52,120 again, it's because of race conditions. 97 00:07:54,670 --> 00:07:57,380 This part of the code is vulnerable to race conditions. 98 00:07:57,400 --> 00:08:00,520 It should only be accessed and updated one thread at a time. 99 00:08:01,480 --> 00:08:06,940 And so what we can do is employ a locking mechanism to ensure that this critical code is indeed accessed 100 00:08:06,940 --> 00:08:08,050 one thread at a time. 101 00:08:08,650 --> 00:08:15,340 So what we can do is create a re entrant like right here entrant lock, lock. 102 00:08:16,100 --> 00:08:19,490 Is equal to a new object of the entrant lock class. 103 00:08:21,960 --> 00:08:24,660 We can pass that log into our incremental function. 104 00:08:29,330 --> 00:08:34,549 And whenever the runtime gets to hear whatever threat it may be, we need to make sure to lock this 105 00:08:34,549 --> 00:08:38,179 part of the code so that it's only access to one thread at a time. 106 00:08:38,600 --> 00:08:44,210 And after the following code has finished running on one thread, then we can unlock our reentry lock 107 00:08:44,900 --> 00:08:48,620 so that another thread who is waiting to access this code can now run it. 108 00:08:49,680 --> 00:08:52,380 OK, and if we run our code now. 109 00:08:54,970 --> 00:08:57,590 We're going to have to pass our lock into here. 110 00:08:58,930 --> 00:09:00,010 If we were in the code. 111 00:09:05,370 --> 00:09:06,870 And these are the correct results. 112 00:09:06,960 --> 00:09:07,470 Beautiful.