About Me

About Me : I have been working as a Software Engineer for various international companies for four years.Currently, I am working as a full stack Javascript developer in Petronas(Malaysia).

Skills

Skills • Javascript •Typescript •Python •C •Java •ReactJs • Redux • VueJs • NestJs • React Testing Library • Django• PostgreSQL • MySQL • NodeJs • Git • Docker • Jira • Visual Studio Code • Slack

সোমবার, ৩০ মে, ২০১৬

uva 929 Number Maze solution

/*********************************   MH RIYAD  *************************************/
#include <bits/stdc++.h>
#include<unordered_set>
#define  pb     push_back
#define  MAX    1010
#define  mod    100000007
#define  read   freopen("input.txt","r",stdin);
#define  write  freopen("output.txt","w",stdout);
#define  inf   (1<<30)
using namespace std;
typedef long long ll ;
typedef unsigned long long ull ;


//struct node
//{
//    int index,w;
//
//};
//bool cmp(node i,node j)
//{
//    return i.w>j.w;
//
//}
//vector<node>v[160006];
//bool mark[160006];
//int main()
//{
//    read;
//    int n,s;
//    scanf("%d",&n);
//    for(int i=2; i<=n*2; i++)
//    {
//        for(int j=1; j<i; j++)
//        {
//            scanf("%d",&s);
//            node no,no2;
//            no.index=i;
//            no.w=s;
//            v[j].pb(no);
//            no2.index=j;
//            no2.w=s;
//            v[i].pb(no2);
//        }
//    }
//
//    for(int i=1; i<=n*2; i++)
//    {
//
//        for(int j=0; j<v[i].size(); j++)
//        {
//            node p=v[i][j];
//            cout<<p.index<<" "<<p.w<<"    ";
//        }
//        cout<<endl;
//    }
//    for(int i=1; i<=n*2; i++)
//    {
//
//        sort(v[i].begin(),v[i].end(),cmp);
//        int len=v[i].size();
//        for(int j=0; j<len; j++)
//        {
//            node p=v[i][j];
//          //  if(!mark[p.w])
//          //  {
//                cout<<p.index<<" ";
//             //   mark[p.w]=true;
//                break;
//           // }
//        }
//    }
//
//    return 0;
//}

int dx[]= {-1,0,0,+1};
int dy[]= {0,+1,-1,0};

struct node
{
    int x,y,w;
    friend bool operator<(node i,node j)
    {
        return i.w>j.w;
    }
};
priority_queue<node>Q;
void dijkstra(int a,int b);
int row,col,graph[MAX][MAX],cost[MAX][MAX];
bool mark[MAX][MAX];
int main()
{
  //  read;
    int test;
    scanf("%d",&test);
    while(test--)
    {
        memset(mark,false,sizeof(mark));
        scanf("%d%d",&row,&col);
        for(int i=0; i<row; i++)
        {
            for(int j=0; j<col; j++)
            {
                scanf("%d",&graph[i][j]);
                cost[i][j]=inf;
            }
        }
        dijkstra(0,0);
        printf("%d\n",cost[row-1][col-1]);
    }
    return 0;
}

void dijkstra(int r,int c)
{
    cost[r][c]=graph[r][c];
    node q;
    q.x=r;
    q.y=c;
    q.w=graph[r][c];
    Q.push(q);

    while(!Q.empty())
    {
        node p=Q.top();
        Q.pop();
        mark[p.x][p.y]=true;
     //   cout<<p.x<<" "<<p.y<<" "<<p.w<<endl;
        for(int i=0; i<4; i++)
        {
            int R=dx[i]+p.x;
            int C=dy[i]+p.y;
            if(R>=0&&R<row&&C>=0&&C<col&&mark[R][C]==false)
            {
                if(cost[p.x][p.y]+graph[R][C]<cost[R][C])
                {
                    cost[R][C]=cost[p.x][p.y]+graph[R][C];
                    node yo;
                    yo.x=R;
                    yo.y=C;
                    yo.w=cost[R][C];
                    Q.push(yo);
                }
            }
        }

    }

}

বৃহস্পতিবার, ২৬ মে, ২০১৬

Two pointer (nice and easy tutorial )

Ref#https://tp-iiita.quora.com/The-Two-Pointer-Algorithm
Introduction
The legendary two pointer approach is one such technique which is less of a talk and more of a discussion on the problems. Binary search is a kind of optimization on the number of trials taken to reach the optimal position and so is the two pointer technique. The approach relies on the sequence following one specific property on which our pointers can move.
Lets try to learn how we apply two pointers and what advantages does they offer us. We will be discussing a lot of problems that may help you to understand the technique better and for that, it is highly recommendable that you sit with a pen and a paper.
Motivation Problem: Given a sorted array  A, having N integers. You need to find any pair(i,j) having sum as given number X.
Constraints:  Array A contains about 105 integers with each having values around 109.
Solution: No doubt, we always have an option of iterating all the array values and finding their corresponding integer Aj having value as X  Ai using binary search. But, lets see how does the two pointer uses the fact that the array is sorted. For this, we keep two pointers, one at the starting tip of the array and another at the tail. Moving on, we now sum up the values contained at both the pointers. In case, value is greater than required sum, we need to shift the right pointer to the left in order to decrease the value by whatever we can since we don't have any other choice. Similarly, if we encounter the sum of values less than required sum, that we can shift the left  pointer, one unit to the right to bring us more closer to required sum. We keep moving the pointers unless we encounter the situation where Al + Ar   reaches the required given sum as X.
C++ implementation of above approach
  1. #define lli long long
  2.  
  3. bool f(lli sum) {
  4. int l = 0, r = n-1; //two pointers
  5. while ( l <= r ) {
  6. if ( A[l] + A[r] == sum ) return 1;
  7. else if ( A[l] + A[r] > sum ) r--;
  8. else l++;
  9. }
  10. return 0;
  11. }
Overall complexity of the above solution is O(N).
Motivation Problem: Given two sorted arrays A and B, each having length Nand M respectively. Form a new sorted merged array having values of both the arrays in sorted format.
Constraints: Array A and  B contains about 105 integers, each having value around 109.
Solution: Since the two arrays are given in sorted order, we can surely do something with two pointers. Let us go step by step.
  1. We will introduce read-indices l1l2 to traverse arrays A and B, respectively. and another write-index cnt to store position of the first free cell in the resulting array. Initially all l1,l2 and cnt will be 0
  2. Moving on, if both indices are in range (l1  < N and l2 < M), choose minimum of (Ai,   Bj) and write it to C[cnt], and increase the respective pointer.
C++ implementation of  the above approach
  1. #define MAX 100005
  2.  
  3. lli C[2*MAX];
  4.  
  5. void merge(lli A[], lli B[])
  6. {
  7. int l1 = 0, l2 = 0, cnt = 0;
  8. while ( l1 < n || l2 < m ) {
  9. if ( l1 < n && l2 < m ) {
  10. if ( A[l1] < B[l2] ) {
  11. C[cnt++] = A[l1];
  12. l1++;
  13. }
  14. else if ( A[l1] > B[l2] ) {
  15. C[cnt++] = B[l2];
  16. l2++;
  17. }
  18. }
  19. else if ( l1 < n ) {
  20. C[cnt++] = A[l1];
  21. l1++;
  22. }
  23. else if ( l2 < m ) {
  24. C[cnt++] = B[l2];
  25. l2++;
  26. }
  27. }
  28. return;
  29. }
We basically traversed both the arrays in the sorted order of combined elements and hence kept inserting the elements into the new array that we needed.
Overall complexity of the solution is O(N+M).  
Move on to the next problem if you are sure, you understood the above problems right and have implemented them yourself. I would like you to think as much as you can in all the problems and question yourself, Why?. Thinking is a healthy process and good for exercising your brain to understand the concepts a lot better.
Motivation Problem: Given an array having N integers, find the contiguous subarray having sum as great as possible, but not greater than M. For details on the statement, refer the problem link here
Constraints: Array can have atmost 105 elements and each number will be non-negative and can be as big as 109.
Solution: As the given array contains positive elements, cumulative sum will indeed be increasing as you go on from left to right in the array. If you have already read the binary search tutorial, I am pretty sure you must have found out a way to solve it already.
Solution using binary search:
  • Store cumulative sum at each index in a separate auxiliary array.
  • Treat each index as startIndex of the required contiguous subarray, find a corresponding endIndex such that the following equation holds true.
cum[endIndex] - cum[startIndex-1] <= M and cum[endIndex+1] - cum[startIndex-1] > M
I leave the implementation for this on the part of the reader to discuss in comments. Now, let us see how can we solve the problem using the two pointers technique.
  • We introduce two pointers l,r  denoting startIndex and endIndex of our contiguous subarray, with both of them at the tip of the array.
  • We now start extending our right pointer r  provided sum[l,r] <= M Once, we reach at such a stage, we don't have any option but to move the left pointer as well and start decreasing the sum until we arrive at the situation where we can extend our right pointer again.
  • As and when we reach the point, where we need to shift the left pointer, we keep updating our maximum sum we have achieved so far.
C++ implementation of the above approach
  1. #include <bits/stdc++.h>
  2. #define lli long long
  3. #define MAX 1000005
  4.  
  5. using namespace std;
  6.  
  7. lli A[MAX];
  8.  
  9. int main()
  10. {
  11. int n;
  12. lli sum = 0;
  13. cin >> n;
  14. for ( int i = 0; i < n; i++ ) cin >> A[i];
  15. int l = 0, r = 0;
  16. lli ans = 0;
  17.  
  18. while ( l < n ) {
  19. while ( r < n && sum + A[r] <= M ) {
  20. sum += A[r];
  21. r++;
  22. }
  23. ans = max(ans, sum);
  24. sum -= A[l];
  25. l++;
  26. }
  27.  
  28. cout << ans << endl;
  29. return 0;
  30. }
That was a lot of fun, learning one topic in such a less amount of time. Excited still!? Lets see how much more you can grasp. Moving on to the next problem...
Motivation Problem: Given an array containing N integers, you need to find the length of the smallest contiguous subarray that contains atleast K distinct elements in it. Output "1" if no such subarray exists.
Constraints: Number of elements in the array are around one million with each of them having value as large as 109 .
Solution: Now, thats where the legendary two pointer technique is the only way to your rescue. If you are reading this, I am pretty much sure that you have read the tutorial on STL containers. The STL container you need to know about here is set.
Going by our own traditional way as we approached in the previous problem, we take two pointers l,r  with both at the tip of the array. We keep on shifting the right pointer unless we have K elements into the set as set will only contains distinct elements and will ignore the insertion of duplicate elements. As soon as we meet our condition, we now shift the left pointer unless the size of the set becomes < K. We also update the length of our minimum contiguous subarray as soon as we are ready to shift the left pointer.
C++ implementation of above approach
  1. int l = 0, r = 0, ans = INF;
  2. map <int , int > cnt;
  3.  
  4. while ( l < n ) {
  5. while ( r < n && s.size() < K ) {
  6. s.insert(A[r]);
  7. cnt[A[r]]++;
  8. r++;
  9. }
  10. if (s.size() >=K) {
  11. ans = min(ans, r-l);
  12. }
  13. if ( cnt[A[l]] == 1 ) s.erase(A[l]);
  14. cnt[A[l]]--;
  15. l++;
  16. }
  17. if ( ans == INF ) ans = -1;
  18. cout << ans << endl;
Great, that was just kind of similar to previous problem. Lets move on to the final problem and you shall be ready to explore.
Motivation Problem:  Given an array having N integers, you need to find out a subsequence of K integers such that these  K integers have the minimum hustle. Hustle of a sequence is defined as sum of pair-wise absolute differences divided by the number of pairs. For details on the statement, refer the problem link here
Constraints: Both N and K are less than or equal to 105 and each element has absolute value of around 109.
Solution: Since, this will be the last problem, let us try to spend some more time discussing the solution in detail.
You really don't want this to be the last problem of the discussion, don't you?
Anyway, lets see what the problem demands this time. The number of pairs in the function wont be of much significance since we will always be dividing by fixed number of C(K,2) pairs. So, we can ignore the denominator here and the way function "hustle"  is defined surely tells us that the numerator of the function will be minimum as much as those K integers will be close to each other. Since, hustle function is nothing but merely summation of absolute difference of pairs. Why not just sort the numbers and consider each consecutive contiguous subarray of length K for this? That's it. You are done for good !
If you still doubt how we have reduced the problem from subsequence of length Kto contiguous substring of length K, try to contradict yourself by removing one element from contiguous K elements and taking some other element, you will surely realize, what wrong happened their and how much the absolute difference increased overall. Try to prove this way to give yourself complete satisfaction about the greedy technique used over here.
C++ implementation of above approach.
  1. #include <bits/stdc++.h>
  2. using namespace std;
  3.  
  4. #define lli long long
  5. #define MAX 1000006
  6.  
  7. lli A[MAX],C[MAX];
  8.  
  9. int main()
  10. {
  11. int l = 1, r = 2, st,en,n;
  12. lli sum,ans;
  13.  
  14. cin >> n >> k;
  15. for ( int i = 1; i <= n; i++ ) cin >> A[i];
  16.  
  17. sort(A+1, A+n+1);
  18.  
  19. cum[0] = 0;
  20. for ( int i = 1; i <= n; i++ ) cum[i] = cum[i-1] + A[i];
  21. while ( r <= k ) {
  22. sum += (A[r]*(r-l) - (cum[r-1] - cum[l-1]));
  23. r++;
  24. }
  25.  
  26. st = 1, en = k, ans = sum;
  27.  
  28. while ( r <= n ) {
  29. sum -= (cum[r-1] - cum[l] - A[l]*(r-l-1));
  30. l++;
  31. sum += (A[r]*(r-l) - (cum[r-1] - cum[l-1]));
  32. if ( ans > sum ) {
  33. ans = sum;
  34. st = l;
  35. en = r;
  36. }
  37. r++;
  38. }
  39. return 0;
  40. }
Overall complexity of the solution is O(NlogN) +