JAVA dp solution with comments
\nclass Solution {\n    \n    int[] dp;\n    \n    public int lengthOfRussianDoll(int index, int[][] envelopes){\n        \n\t\t// terminating condition aka bas
```\nclass Solution {\n    \n    int[] dp;\n    \n    public int lengthOfRussianDoll(int index, int[][] envelopes){\n        \n\t\t// terminating condition aka base case\n        if(index > envelopes.length-1)\n            return 0;\n        \n        if(dp[index] > 0)\n            return dp[index];\n\n        int maxCount = 0;\n        \n\t\t// main recursive module\n        for(int i=index+1;i<envelopes.length;i++){\n\t\t\t// check if i envelope can be put inside index envelope\n            if(envelopes[index][1] > envelopes[i][1] && envelopes[index][0] > envelopes[i][0])\n                maxCount = Math.max(maxCount, lengthOfRussianDoll(i,envelopes)+1);\n        }\n        \n        dp[index] = maxCount;\n        \n        return dp[index];\n    }\n    \n    public int maxEnvelopes(int[][] envelopes) {\n        // edge cases\n        if(envelopes == null || envelopes.length == 0)\n            return 0;\n        \n\t\t// sort the array on envelopes with width descending order.\n        Arrays.sort(envelopes, new Comparator<int[]>(){\n            @Override\n            public int compare(int[] a1, int[] a2){\n                return a2[0] - a1[0];\n            }\n        });\n        \n\t\t// dp[index] gives the maxium length of russian doll taking index as the outer most envelope.\n        dp = new int[envelopes.length];\n        \n\t\t// Now we consider creating the russian doll sequence with considering each envelope as the\n\t\t// outermost envelope and then moving forward. The important thing about sorting is than for any\n\t\t// index i ....only possible indexes will be greater than i. \n        int maxCount = 0;\n        for(int i=0;i<envelopes.length;i++){\n            maxCount = Math.max(maxCount, lengthOfRussianDoll(i,envelopes)+1);        \n        }\n        \n        return maxCount;\n        \n    }\n}\n```
[]