├── .gitignore ├── README.md ├── arrays ├── CyclicRotation.java └── OddOccurrencesInArray.java ├── countingElements ├── FrogRiverOne.java ├── MaxCounters.java ├── MissingInteger.java └── PermCheck.java ├── iterations └── BinaryGap.java ├── leader ├── Dominator.java └── EquiLeader.java ├── prefixSums ├── CountDiv.java ├── GenomicRangeQuery.java ├── MinAvgTwoSlice.java └── PassingCars.java ├── sorting ├── Distinct.java ├── MaxProductOfThree ├── NumberOfDiscIntersections.java └── Triangle.java ├── stacksAndQueues ├── Brackets.java ├── Fish.java ├── Nesting.java └── StoneWall.java └── timeComplexity ├── FrogJmp.java ├── PermMissingElem.java └── TapeEquilibrium.java /.gitignore: -------------------------------------------------------------------------------- 1 | # Compiled class file 2 | *.class 3 | 4 | # Log file 5 | *.log 6 | 7 | # BlueJ files 8 | *.ctxt 9 | 10 | # Mobile Tools for Java (J2ME) 11 | .mtj.tmp/ 12 | 13 | # Package Files # 14 | *.jar 15 | *.war 16 | *.nar 17 | *.ear 18 | *.zip 19 | *.tar.gz 20 | *.rar 21 | 22 | # virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml 23 | hs_err_pid* 24 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Codility Practice Sessions 2 | 3 | My 100% scoring solutions for [Codility practice sessions](https://app.codility.com/programmers/lessons/) 4 | 5 | ## Lesson 1 - Iterations 6 | [Binary Gap](iterations/BinaryGap.java) 7 | 8 | ## Lesson 2 - Arrays 9 | [CyclicRotation](arrays/CyclicRotation.java) 10 | 11 | [OddOccurrencesInArray](arrays/OddOccurrencesInArray.java) 12 | 13 | ## Lesson 3 - Time Complexity 14 | [FrogJmp](timeComplexity/FrogJmp.java) 15 | 16 | [PermMissingElem](timeComplexity/PermMissingElem.java) 17 | 18 | [TapeEquilibrium](timeComplexity/TapeEquilibrium.java) 19 | 20 | ## Lesson 4 - Counting Elements 21 | [FrogRiverOne](countingElements/FrogRiverOne.java) 22 | 23 | [MissingInteger](countingElements/MissingInteger.java) 24 | 25 | [PermCheck](countingElements/PermCheck.java) 26 | 27 | [MaxCounters](countingElements/MaxCounters.java) 28 | 29 | ## Lesson 5 - Prefix Sums 30 | [CountDiv](prefixSums/CountDiv.java) 31 | 32 | [PassingCars](prefixSums/PassingCars.java) 33 | 34 | [GenomicRangeQuery](prefixSums/GenomicRangeQuery.java) 35 | 36 | [MinAvgTwoSlice](prefixSums/MinAvgTwoSlice.java) 37 | 38 | ## Lesson 6 - Sorting 39 | [Distinct](sorting/Distinct.java) 40 | 41 | [MaxProductOfThree](sorting/MaxProductOfThree.java) 42 | 43 | [Triangle](sorting/Triangle.java) 44 | 45 | [NumberOfDiscIntersections](sorting/NumberOfDiscIntersections.java) 46 | 47 | ## Lesson 7 - Stacks and Queues 48 | [Nesting](stacksAndQueues/Nesting.java) 49 | 50 | [Brackets](stacksAndQueues/Brackets.java) 51 | 52 | [Fish](stacksAndQueues/Fish.java) 53 | 54 | [StoneWall](stacksAndQueues/StoneWall.java) 55 | 56 | ## Lesson 8 - Leader 57 | [Dominator](leader/Dominator.java) 58 | 59 | [EquiLeader](leader/EquiLeader.java) 60 | -------------------------------------------------------------------------------- /arrays/CyclicRotation.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | 7 | class Solution { 8 | public int[] solution(int[] A, int K) { 9 | int len = A.length; 10 | if(len == 0) { return A; } 11 | 12 | K %= len; 13 | if(K == 0) { return A; } 14 | 15 | rotate(A, K); 16 | 17 | return A; 18 | } 19 | 20 | private void rotate(int[]A, int K) { 21 | int len = A.length; 22 | 23 | int bucket = gcd(len, K); 24 | 25 | // ...I are index variables, ..E are element/value variables 26 | // there are as many buckets/groups as gcd 27 | // algorithm should loop for each bucket 28 | // current element is kept 29 | // jump to K elements forward (might be cyclic, use modular arithmetic) 30 | // put kept element in here and keep element that is already there (need a swap variable) 31 | // continue with jumping K elements forward, until you are at where you started 32 | // do this for each bucket 33 | for(int i=0; i to map each index as real leaf position 13 | // .. easier for claculations 14 | boolean[] isLeafFallAtPointArr = new boolean[X+1]; 15 | 16 | // counts the first leaf at each point 17 | // .. since only that is useful to frog 18 | // .. for frog, there should be exactly X useful leaves 19 | int usefulLeafCounter = 0; 20 | 21 | // looping array, fill isLeafFallAtPointArr to track whether leaf fall at that point 22 | // doing that keep track of actual set operations (usefulLeafCounter) 23 | // .. to make sure every point filled (should be X set operations) 24 | for(int i=0; i maxSoFar) { maxSoFar = counterArr[val-1]; } 23 | } 24 | 25 | // handleMaxCounter 26 | else { 27 | // do not need to fill counter array actually 28 | // Arrays.fill(counterArr, maxSoFar); 29 | actualMaxSoFar = maxSoFar; 30 | } 31 | } 32 | 33 | patch4ActualMaxSoFar(counterArr, actualMaxSoFar); 34 | 35 | return counterArr; 36 | } 37 | 38 | private void patch4ActualMaxSoFar(int[] counterArr, int actualMaxSoFar) { 39 | for(int i=0; i= A.length + 1 ) { continue; } 26 | 27 | if ( !isIntExist[val] ) { isIntExist[val] = true; } 28 | } 29 | } 30 | 31 | private int findMaxConsecutiveInt(boolean[] isIntExist) { 32 | // since 1-indexing.. 33 | for(int i=1; i len || isIntExist[val]) return 0; 18 | isIntExist[val] = true; 19 | } 20 | 21 | return checkForPermutation(isIntExist); 22 | } 23 | 24 | private int checkForPermutation(boolean[] isIntExist) { 25 | // since 1-indexing, skip 0th index 26 | for(int i=1; i 0) { 13 | if(isOne(N)) { 14 | maxGap = maxGap < currGap ? currGap : maxGap; 15 | currGap = 0; 16 | isInGap = true; 17 | } else if(isInGap){ currGap++; } 18 | N /= 2; 19 | } 20 | 21 | return maxGap; 22 | } 23 | 24 | private boolean isOne(int N) { 25 | return N%2 == 1 || N == 1 ; 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /leader/Dominator.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | import java.util.Stack; 7 | 8 | class Solution { 9 | public int solution(int[] A) { 10 | // majority vote algorithm 11 | int candidateIndex = -1; 12 | int counter = 0; 13 | 14 | for(int i=0; i 0) { counter--; } 30 | else { 31 | counter = 0; 32 | candidateIndex = i; 33 | } 34 | } 35 | } 36 | 37 | return (isDominator(A, candidateIndex)) ? candidateIndex : -1; 38 | } 39 | 40 | private boolean isDominator(int[] A, int candidateIndex) { 41 | if(candidateIndex < 0) return false; 42 | 43 | int countOfCandidate = 0; 44 | 45 | for(int element: A) { 46 | if(element == A[candidateIndex]) { countOfCandidate++; } 47 | } 48 | 49 | return (countOfCandidate > A.length/2) ? true : false; 50 | } 51 | } 52 | -------------------------------------------------------------------------------- /leader/EquiLeader.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | import java.util.*; 7 | 8 | class Solution { 9 | public int solution(int[] A) { 10 | // Algorithm: find leader in one iteration - O(len) 11 | // .. use two prefix arrays to keep leader so far - space O(len) 12 | // .. make to passes - forward and backward and mark if leader is leader so far 13 | // .. once prefix arrays are ready, check forward prefix array i, backward i+1 14 | // .. if both leader, i is a split point - count that 15 | 16 | int len = A.length; 17 | boolean[] forwardLeaderCheckArray = new boolean[len]; 18 | boolean[] backwardLeaderCheckArray = new boolean[len]; 19 | 20 | int leader = computeLeader(A); 21 | 22 | // forward pass 23 | int countSoFar = 0; 24 | for(int i=0; i 0.5 ) { forwardLeaderCheckArray[i] = true; } 27 | } 28 | 29 | // backward pass 30 | countSoFar = 0; 31 | for(int i=len-1; i>=0; i--) { 32 | if(A[i] == leader ) { countSoFar++; } 33 | if( (double)countSoFar / (len-i) > 0.5 ) { backwardLeaderCheckArray[i] = true; } 34 | } 35 | 36 | // evaluate 37 | int numOfSplits = 0; 38 | for(int i=1; i 0) { minImpactArr[i] = 1; } 48 | else if(prefixC[end] - prefixC[start] > 0) { minImpactArr[i] = 2; } 49 | else if(prefixG[end] - prefixG[start] > 0) { minImpactArr[i] = 3; } 50 | else { minImpactArr[i] = 4; } 51 | } 52 | 53 | return minImpactArr; 54 | } 55 | 56 | } 57 | -------------------------------------------------------------------------------- /prefixSums/MinAvgTwoSlice.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | 7 | class Solution { 8 | public int solution(int[] A) { 9 | // slices can only be 2 or 3 in length (mathematically) 10 | // .. prefix sum at starting index - avg with next item 11 | // .. can be dome in space 12 | 13 | double minAvg = Double.MAX_VALUE; 14 | int minAvgIndex = 0; 15 | 16 | for(int i=0; i avg) { 24 | minAvg = avg; 25 | minAvgIndex = i; 26 | } 27 | } 28 | 29 | return minAvgIndex; 30 | } 31 | } 32 | -------------------------------------------------------------------------------- /prefixSums/PassingCars.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | 7 | class Solution { 8 | public int solution(int[] A) { 9 | // 0: east --> 10 | // 1: west <-- 11 | // p: --> 12 | // q: <-- passing 13 | // for each left 0, there are as many passing cars as 1 s on its right 14 | // in other words, 15 | // ... for each 1, there are as many passing cars as 0 s on its left 16 | 17 | int eastCount = 0; 18 | int passingCount = 0; 19 | 20 | for(int val: A) { 21 | if(val == 0) { eastCount++; } 22 | else { passingCount += eastCount; } 23 | 24 | if(passingCount > 1000000000) return -1; 25 | } 26 | 27 | return passingCount; 28 | } 29 | } 30 | -------------------------------------------------------------------------------- /sorting/Distinct.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | import java.util.Arrays; 7 | 8 | class Solution { 9 | public int solution(int[] A) { 10 | if(A.length == 0) { return 0; } 11 | 12 | int numOfDistinct = 1; 13 | Arrays.sort(A); 14 | 15 | for(int i=1; i= len ? len - 1 : i + A[i]; 30 | numOfCirclesEndingArr[ending]++; 31 | } 32 | 33 | // calculate number of intersections using 34 | // num of circles starting and ending each point between [0 - len) 35 | int numOfIntersects = 0; 36 | int numOfActiveCircles = 0; 37 | for(int i=0; i10000000) return -1; 43 | numOfActiveCircles += numOfCirclesStartingArr[i]-numOfCirclesEndingArr[i]; 44 | } 45 | 46 | return numOfIntersects; 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /sorting/Triangle.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | 7 | import java.util.Arrays; 8 | 9 | class Solution { 10 | public int solution(int[] A) { 11 | // sort array 12 | // linearly check for triangle property 13 | 14 | Arrays.sort(A); 15 | 16 | for(int i=0; i A[startIndex+2] && 25 | calcSum(A[startIndex+2], A[startIndex]) > A[startIndex+1] && 26 | calcSum(A[startIndex+1], A[startIndex+2]) > A[startIndex] ) { return true; } 27 | 28 | return false; 29 | } 30 | 31 | // when max int is possible, 32 | // ..sum should handle in long - since it cannot fit and overflow 33 | private long calcSum(int a, int b) { 34 | return (new Long(a) + new Long(b)); 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /stacksAndQueues/Brackets.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | import java.util.Stack; 7 | 8 | class Solution { 9 | public int solution(String S) { 10 | String openBrackets = "{[("; 11 | String closeBrackets = "}])"; 12 | 13 | Stack stack = new Stack<>(); 14 | 15 | for(char c: S.toCharArray()) { 16 | if(isInBrackets(c, openBrackets)) { stack.push(c); } 17 | else { 18 | if(stack.isEmpty() || 19 | stack.pop() != getCorrespondingOpenBracket(c, openBrackets, closeBrackets)) 20 | { return 0; } 21 | } 22 | } 23 | 24 | if(stack.isEmpty()) return 1; 25 | return 0; 26 | } 27 | 28 | private boolean isInBrackets(char c, String brackets) { 29 | if(brackets.indexOf(c) >= 0) { return true; } 30 | return false; 31 | } 32 | 33 | private char getCorrespondingOpenBracket(char closeBracket, String openBrackets, String closeBrackets) { 34 | return openBrackets.charAt(closeBrackets.indexOf(closeBracket)); 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /stacksAndQueues/Fish.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | import java.util.Stack; 7 | 8 | class Solution { 9 | public int solution(int[] A, int[] B) { 10 | // sizes --> A 11 | // directions --> B 0:upstream 1:downstream 12 | int len = A.length; 13 | Stack upstreamStack = new Stack<>(); 14 | Stack downstreamStack = new Stack<>(); 15 | 16 | for(int i=0; i downstreamStack.peek() ) { 28 | downstreamStack.pop(); 29 | } 30 | 31 | if(downstreamStack.isEmpty()) { upstreamStack.push(size); } 32 | } 33 | } 34 | 35 | return downstreamStack.size() + upstreamStack.size(); 36 | 37 | } 38 | } 39 | -------------------------------------------------------------------------------- /stacksAndQueues/Nesting.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | import java.util.Stack; 7 | 8 | class Solution { 9 | public int solution(String S) { 10 | Stack stack = new Stack<>(); 11 | 12 | for(Character c: S.toCharArray()) { 13 | if(c == '(') { stack.push(c); } 14 | else { 15 | if( stack.isEmpty() ) { return 0; } 16 | stack.pop(); 17 | } 18 | } 19 | 20 | if(stack.isEmpty()) { return 1; } 21 | 22 | return 0; 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /stacksAndQueues/StoneWall.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | 7 | // https://codility.com/media/train/solution-stone-wall.pdf 8 | 9 | import java.util.Stack; 10 | 11 | class Solution { 12 | public int solution(int[] H) { 13 | // Greedy Algorithm: 14 | // Build the bottoms as much as common as possible 15 | // .. for that, keen track of heights in a stack 16 | // .. while iterating, if current building can be built using stone at top of stack 17 | // .. than no new stone is needed 18 | // .. if current building is higher, new stone is needed and top of stack is updated 19 | // .. if current building is lower, top of stack is popped until we find a <= height stone 20 | // .. in stack, then new stone is needed for previous ones 21 | // .. and current height is pushed to stack 22 | Stack stackOfHeights = new Stack<>(); 23 | int numOfStones = 0; 24 | 25 | for(int currentHeight: H) { 26 | while( !stackOfHeights.isEmpty() && stackOfHeights.peek() > currentHeight) { 27 | stackOfHeights.pop(); 28 | } 29 | 30 | if(!stackOfHeights.isEmpty()) { 31 | if(stackOfHeights.peek() == currentHeight) { continue; } 32 | else { 33 | numOfStones++; 34 | stackOfHeights.push(currentHeight); 35 | } 36 | } else { 37 | numOfStones++; 38 | stackOfHeights.push(currentHeight); 39 | } 40 | } 41 | 42 | return numOfStones; 43 | } 44 | } 45 | -------------------------------------------------------------------------------- /timeComplexity/FrogJmp.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | 7 | class Solution { 8 | public int solution(int X, int Y, int D) { 9 | 10 | int initialJumpCount = (Y-X) / D; 11 | int remainingJumpCount = (Y-X) % D; 12 | 13 | return 14 | (remainingJumpCount > 0 ? initialJumpCount + 1: initialJumpCount); 15 | 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /timeComplexity/PermMissingElem.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | 7 | class Solution { 8 | public int solution(int[] A) { 9 | // since all distinct, we are safe.. some controls can be omitted 10 | // if the missing also available, sum would be n (n + 1) / 2 where n = length (A) + 1 11 | // tip: sums should be long, since might overflow for large n 12 | long shouldBeLength = A.length + 1; 13 | long shouldBeSum = shouldBeLength * (shouldBeLength + 1) / 2; 14 | 15 | return (int) (shouldBeSum - calcSum(A)); 16 | 17 | } 18 | 19 | private long calcSum(int[] A) { 20 | long sum = 0; 21 | 22 | for(int elem: A) { sum += elem; } 23 | 24 | return sum; 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /timeComplexity/TapeEquilibrium.java: -------------------------------------------------------------------------------- 1 | // you can also use imports, for example: 2 | // import java.util.*; 3 | 4 | // you can write to stdout for debugging purposes, e.g. 5 | // System.out.println("this is a debug message"); 6 | 7 | class Solution { 8 | public int solution(int[] A) { 9 | // cumulative approach works - two passes 10 | // first pass (left to right): at each point we can store left sum for that point 11 | // .. no additional space is required, we can update array A 12 | // .. since an element is equal to its diff with its left element (calculatable) 13 | // second point (right to left): at each point we can calculate right sum (no need to store) 14 | // .. and since both left and right sums known at second pass, take diff and search for min 15 | 16 | // first pass 17 | calculateLeftSums(A); 18 | 19 | // second pass 20 | return findMinDiffPoint(A); 21 | 22 | } 23 | 24 | private void calculateLeftSums(int[] A) { 25 | // sure A has at least 2 elements from task spec 26 | for(int i=1; i 0; i--) { 35 | rightSum += A[i] - A[i-1]; 36 | int diff = Math.abs( rightSum - A[i-1] ); 37 | if( diff < minDiff ) {minDiff = diff;} 38 | } 39 | 40 | return minDiff; 41 | } 42 | } 43 | --------------------------------------------------------------------------------