Upgrade to Pro — share decks privately, control downloads, hide ads and more …

SE103 - Week 9, Session 2

Caren
August 08, 2020

SE103 - Week 9, Session 2

Caren

August 08, 2020
Tweet

More Decks by Caren

Other Decks in Education

Transcript

  1. Week 9:
    Dynamic Programming,
    Continued!

    View Slide

  2. - Fibonacci
    - Knapsack
    - Unbounded knapsack
    - Palindromic Sequences
    - Common Substrings
    Common Patterns in DP

    View Slide

  3. - Fibonacci
    - Knapsack
    - Unbounded knapsack
    - Palindromic Sequences
    - Common Substrings
    Common Patterns in DP

    View Slide

  4. Given a string, find the length of its Longest
    Palindromic Subsequence (LPS). In a palindromic
    subsequence, elements read the same backward
    and forward.
    A subsequence is a sequence that can be derived
    from another sequence by deleting some or no
    elements without changing the order of the remaining
    elements.
    Longest Palindromic Subsequence

    View Slide

  5. Given a string, find the length of its Longest Palindromic Subsequence
    (LPS). In a palindromic subsequence, elements read the same
    backward and forward.
    Example 1

    Given: abdbca

    Return: ??
    Longest Palindromic Subsequence

    View Slide

  6. Given a string, find the length of its Longest Palindromic Subsequence
    (LPS). In a palindromic subsequence, elements read the same
    backward and forward.
    Example 1

    Given: abdbca

    Return: 5 (abdba)
    Longest Palindromic Subsequence

    View Slide

  7. Given a string, find the length of its Longest Palindromic Subsequence
    (LPS). In a palindromic subsequence, elements read the same
    backward and forward.
    Example 1

    Given: abdbca

    Return: 5 (abdba)
    Example 2

    Given: cddpd

    Return: ??
    Longest Palindromic Subsequence

    View Slide

  8. Given a string, find the length of its Longest Palindromic Subsequence
    (LPS). In a palindromic subsequence, elements read the same
    backward and forward.
    Example 1

    Given: abdbca

    Return: 5 (abdba)
    Example 2

    Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence

    View Slide

  9. Given a string, find the length of its Longest Palindromic Subsequence
    (LPS). In a palindromic subsequence, elements read the same
    backward and forward.
    Example 1

    Given: abdbca

    Return: 5 (abdba)
    Example 2

    Given: cddpd

    Return: 3 (ddd or dpd)


    Example 3

    Given: abc

    Return: ??

    Longest Palindromic Subsequence

    View Slide

  10. Given a string, find the length of its Longest Palindromic Subsequence
    (LPS). In a palindromic subsequence, elements read the same
    backward and forward.
    Example 1

    Given: abdbca

    Return: 5 (abdba)
    Example 2

    Given: cddpd

    Return: 3 (ddd or dpd)


    Example 3

    Given: abc

    Return: 1 (a or b or c)

    Longest Palindromic Subsequence

    View Slide

  11. Given: cddpd

    Return: 3 (ddd or dpd)
    Intuitively…

    Let’s have two pointers, one starting at the beginning and one starting
    at the end

    cddpd



    Longest Palindromic Subsequence

    View Slide

  12. Given: cddpd

    Return: 3 (ddd or dpd)
    Intuitively…

    Let’s have two pointers, one starting at the beginning and one starting
    at the end

    cddpd



    If the letters are the same

    - count of palindromic subsequence = 2

    - recurively do this for the rest of the substring


    Longest Palindromic Subsequence

    View Slide

  13. Given: cddpd

    Return: 3 (ddd or dpd)
    Intuitively…

    Let’s have two pointers, one starting at the beginning and one starting
    at the end

    cddpd



    If the letters are the same

    - count of palindromic subsequence = 2

    if letters are NOT the same

    - try advancing starting pointer cddpd


    - try advancing ending pointer cddpd
    Longest Palindromic Subsequence

    View Slide

  14. Longest Palindromic Subsequence
    cddpd

    View Slide

  15. Longest Palindromic Subsequence
    c != d
    cddpd

    View Slide

  16. Longest Palindromic Subsequence
    c != d
    cddpd
    ddpd cddp

    View Slide

  17. Longest Palindromic Subsequence
    c != d
    cddpd
    ddpd cddp
    d == d

    count = 2

    View Slide

  18. Longest Palindromic Subsequence
    c != d
    cddpd
    ddpd cddp
    c != p
    d == d

    count = 2

    View Slide

  19. Longest Palindromic Subsequence
    c != d
    cddpd
    ddpd cddp
    c != p
    d == d

    count = 2
    dp

    View Slide

  20. Longest Palindromic Subsequence
    c != d
    cddpd
    ddpd cddp
    c != p
    d == d

    count = 2
    dp
    d != p
    p d

    View Slide

  21. Longest Palindromic Subsequence
    c != d
    cddpd
    ddpd cddp
    c != p
    d == d

    count = 2
    dp
    d != p
    p d
    p == p
    count = 1
    d == d
    count = 1

    View Slide

  22. Longest Palindromic Subsequence
    c != d
    cddpd
    ddpd cddp
    c != p
    d == d

    count = 2
    dp
    d != p
    p d
    p == p
    count = 1
    d == d
    count = 1
    2 + Max(1, 1) = 3

    View Slide

  23. Longest Palindromic Subsequence
    c != d
    cddpd
    ddpd cddp
    c != p
    d == d

    count = 2
    dp
    d != p
    p d
    p == p
    count = 1
    d == d
    count = 1
    2 + 1 = 3
    if(startIndex == endIndex)
    return 1;
    // case 1: beginning and the end are the same
    if(st.charAt(startIndex) == st.charAt(endIndex))
    return 2 + lpsLengthRecursive(st, startIndex+1, endIndex-1);
    // case 2: skip one element either from the beginning or the end
    int r1 = lpsLengthRecursive(startIndex+1, endIndex);
    int r2 = lpsLengthRecursive(startIndex, endIndex-1);
    return Math.max(r1, r2);
    Run time: ??

    View Slide

  24. Longest Palindromic Subsequence
    c != d
    cddpd
    ddpd cddp
    c != p
    d == d

    count = 2
    dp
    d != p
    p d
    p == p
    count = 1
    d == d
    count = 1
    2 + 1 = 3
    if(startIndex == endIndex)
    return 1;
    // case 1: beginning and the end are the same
    if(st.charAt(startIndex) == st.charAt(endIndex))
    return 2 + lpsLengthRecursive(st, startIndex+1, endIndex-1);
    // case 2: skip one element either from the beginning or the end
    int r1 = lpsLengthRecursive(startIndex+1, endIndex);
    int r2 = lpsLengthRecursive(startIndex, endIndex-1);
    return Math.max(r1, r2);
    Run time: 2 ^ n
    if(startIndex == endIndex)
    return 1;
    // case 1: beginning and the end are the same
    if(st.charAt(startIndex) == st.charAt(endIndex))
    return 2 + lpsLengthRecursive(st, startIndex+1, endIndex-1);
    // case 2: skip one element either from the beginning or the end
    int r1 = lpsLengthRecursive(startIndex+1, endIndex);
    int r2 = lpsLengthRecursive(startIndex, endIndex-1);
    return Math.max(r1, r2);

    View Slide

  25. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    c d d p d
    0 1 2 3 4
    ending index

    View Slide

  26. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    length = 1

    View Slide

  27. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1
    1
    1
    1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    length = 1

    View Slide

  28. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1
    1
    1
    1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    length = 2

    View Slide

  29. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1
    1
    1
    1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    length = 2
    what substring is this?

    View Slide

  30. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1
    1
    1
    1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    length = 2
    “cd”

    View Slide

  31. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 1
    1
    1
    1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    length = 2
    “cd”

    View Slide

  32. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 1
    1
    1
    1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    length = 2
    “dd”

    View Slide

  33. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 1
    1 2
    1
    1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    length = 2
    “dd”

    View Slide

  34. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 1
    1 2
    1 1
    1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    length = 2
    “dp”

    View Slide

  35. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 1
    1 2
    1 1
    1 1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    length = 2
    “pd”

    View Slide

  36. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 1
    1 2
    1 1
    1 1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    length = 3

    View Slide

  37. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 1
    1 2
    1 1
    1 1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    “cdd”
    max of “cd,”
    and “dd”

    View Slide

  38. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 1 2
    1 2
    1 1
    1 1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    “cdd”
    max of “cd,”
    and “dd”

    View Slide

  39. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 1 2
    1 2 2
    1 1
    1 1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    “ddp”
    max of “dd,”
    and “dp”

    View Slide

  40. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 1 2
    1 2 2
    1 1
    1 1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    “dpd”
    max of “dp,”
    and “pd”

    View Slide

  41. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 1 2
    1 2 2
    1 1
    1 1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    “dpd”
    max of “dp,”
    and “pd”
    … 1?!?

    View Slide

  42. Given: cddpd

    Return: 3 (ddd or dpd)
    Longest Palindromic Subsequence
    1 1 2
    1 2 2
    1 1 3
    1 1
    1
    1 2 3 4
    0
    0
    1
    2
    3
    4
    starting index
    ending index
    c d d p d
    0 1 2 3 4
    “dpd”
    If start == end,
    2 + start[+1]end[-1]

    (“p”)

    View Slide

  43. // create dp[][] array
    dp[i][i] = 1; // every length 1 substring
    for (int startIndex = s.length() - 1; startIndex >= 0; startIndex--) {
    for (int endIndex = startIndex + 1; endIndex < s.length(); endIndex++) {
    // case 1: letter at the beginning and the end are the same
    if (s.charAt(startIndex) == s.charAt(endIndex)) {
    dp[startIndex][endIndex] = 2 + dp[startIndex + 1][endIndex - 1];
    } else {
    // case 2: skip one element either from the beginning or the end
    dp[startIndex][endIndex] = Math.max(
    dp[startIndex + 1][endIndex],
    dp[startIndex][endIndex - 1]);
    }
    }
    }
    return dp[0][st.length() - 1];

    View Slide

  44. // create dp[][] array
    dp[i][i] = 1; // every length 1 substring
    for (int startIndex = s.length() - 1; startIndex >= 0; startIndex--) {
    for (int endIndex = startIndex + 1; endIndex < s.length(); endIndex++) {
    // case 1: letter at the beginning and the end are the same
    if (s.charAt(startIndex) == s.charAt(endIndex)) {
    dp[startIndex][endIndex] = 2 + dp[startIndex + 1][endIndex - 1];
    } else {
    // case 2: skip one element either from the beginning or the end
    dp[startIndex][endIndex] = Math.max(
    dp[startIndex + 1][endIndex],
    dp[startIndex][endIndex - 1]);
    }
    }
    }
    return dp[0][st.length() - 1];
    start
    end

    View Slide

  45. // create dp[][] array
    dp[i][i] = 1; // every length 1 substring
    for (int startIndex = s.length() - 1; startIndex >= 0; startIndex--) {
    for (int endIndex = startIndex + 1; endIndex < s.length(); endIndex++) {
    // case 1: letter at the beginning and the end are the same
    if (s.charAt(startIndex) == s.charAt(endIndex)) {
    dp[startIndex][endIndex] = 2 + dp[startIndex + 1][endIndex - 1];
    } else {
    // case 2: skip one element either from the beginning or the end
    dp[startIndex][endIndex] = Math.max(
    dp[startIndex + 1][endIndex],
    dp[startIndex][endIndex - 1]);
    }
    }
    }
    return dp[0][st.length() - 1];
    start
    end

    View Slide

  46. // create dp[][] array
    dp[i][i] = 1; // every length 1 substring
    for (int startIndex = s.length() - 1; startIndex >= 0; startIndex--) {
    for (int endIndex = startIndex + 1; endIndex < s.length(); endIndex++) {
    // case 1: letter at the beginning and the end are the same
    if (s.charAt(startIndex) == s.charAt(endIndex)) {
    dp[startIndex][endIndex] = 2 + dp[startIndex + 1][endIndex - 1];
    } else {
    // case 2: skip one element either from the beginning or the end
    dp[startIndex][endIndex] = Math.max(
    dp[startIndex + 1][endIndex],
    dp[startIndex][endIndex - 1]);
    }
    }
    }
    return dp[0][st.length() - 1];
    start
    end

    View Slide

  47. // create dp[][] array
    dp[i][i] = 1; // every length 1 substring
    for (int startIndex = s.length() - 1; startIndex >= 0; startIndex--) {
    for (int endIndex = startIndex + 1; endIndex < s.length(); endIndex++) {
    // case 1: letter at the beginning and the end are the same
    if (s.charAt(startIndex) == s.charAt(endIndex)) {
    dp[startIndex][endIndex] = 2 + dp[startIndex + 1][endIndex - 1];
    } else {
    // case 2: skip one element either from the beginning or the end
    dp[startIndex][endIndex] = Math.max(
    dp[startIndex + 1][endIndex],
    dp[startIndex][endIndex - 1]);
    }
    }
    }
    return dp[0][st.length() - 1];
    start
    end

    View Slide

  48. // create dp[][] array
    dp[i][i] = 1; // every length 1 substring
    for (int startIndex = s.length() - 1; startIndex >= 0; startIndex--) {
    for (int endIndex = startIndex + 1; endIndex < s.length(); endIndex++) {
    // case 1: letter at the beginning and the end are the same
    if (s.charAt(startIndex) == s.charAt(endIndex)) {
    dp[startIndex][endIndex] = 2 + dp[startIndex + 1][endIndex - 1];
    } else {
    // case 2: skip one element either from the beginning or the end
    dp[startIndex][endIndex] = Math.max(
    dp[startIndex + 1][endIndex],
    dp[startIndex][endIndex - 1]);
    }
    }
    }
    return dp[0][st.length() - 1];
    start
    end

    View Slide

  49. // create dp[][] array
    dp[i][i] = 1; // every length 1 substring
    for (int startIndex = s.length() - 1; startIndex >= 0; startIndex--) {
    for (int endIndex = startIndex + 1; endIndex < s.length(); endIndex++) {
    // case 1: letter at the beginning and the end are the same
    if (s.charAt(startIndex) == s.charAt(endIndex)) {
    dp[startIndex][endIndex] = 2 + dp[startIndex + 1][endIndex - 1];
    } else {
    // case 2: skip one element either from the beginning or the end
    dp[startIndex][endIndex] = Math.max(
    dp[startIndex + 1][endIndex],
    dp[startIndex][endIndex - 1]);
    }
    }
    }
    return dp[0][st.length() - 1];
    start
    end

    View Slide

  50. // create dp[][] array
    dp[i][i] = 1; // every length 1 substring
    for (int startIndex = s.length() - 1; startIndex >= 0; startIndex--) {
    for (int endIndex = startIndex + 1; endIndex < s.length(); endIndex++) {
    // case 1: letter at the beginning and the end are the same
    if (s.charAt(startIndex) == s.charAt(endIndex)) {
    dp[startIndex][endIndex] = 2 + dp[startIndex + 1][endIndex - 1];
    } else {
    // case 2: skip one element either from the beginning or the end
    dp[startIndex][endIndex] = Math.max(
    dp[startIndex + 1][endIndex],
    dp[startIndex][endIndex - 1]);
    }
    }
    }
    return dp[0][st.length() - 1];

    View Slide

  51. // create dp[][] array
    dp[i][i] = 1; // every length 1 substring
    for (int startIndex = s.length() - 1; startIndex >= 0; startIndex--) {
    for (int endIndex = startIndex + 1; endIndex < s.length(); endIndex++) {
    // case 1: letter at the beginning and the end are the same
    if (s.charAt(startIndex) == s.charAt(endIndex)) {
    dp[startIndex][endIndex] = 2 + dp[startIndex + 1][endIndex - 1];
    } else {
    // case 2: skip one element either from the beginning or the end
    dp[startIndex][endIndex] = Math.max(
    dp[startIndex + 1][endIndex],
    dp[startIndex][endIndex - 1]);
    }
    }
    }
    return dp[0][st.length() - 1];

    View Slide

  52. What did we learn?

    View Slide

  53. - Solving it ‘naively’ first helps come up with DP
    approach
    - Recursive -> bottom up approach
    - Palindromic questions -> two pointers, one at start
    and one at end
    What did we learn?

    View Slide

  54. 2 problems
    30 minutes for each problem
    Pick the person that has their birthday coming up
    next!
    Mock Interviews

    View Slide

  55. How did it go??

    View Slide

  56. - DP problems are hard, practice is key

    - We didn’t cover DP + Binary Trees, would
    recommend spending some time practicing that
    - HackerRank
    - More practice next week!
    Before next session

    View Slide

  57. Journey of Caren’s career

    View Slide

  58. Interned at Dreamworks for two semesters


    View Slide

  59. Interned at Dreamworks for two semesters

    -> realized I didn’t like big companies

    View Slide

  60. Interned at Dreamworks 

    -> realized I didn’t like big companies
    Recruited a bunch senior year, failed a bunch of interviews

    View Slide

  61. Interned at Dreamworks 

    -> realized I didn’t like big companies
    Recruited a bunch senior year, failed a bunch of interviews
    Got a full time offer at a financial startup (75k) -> wasn’t really excited, but
    wanted a job

    View Slide

  62. Interned at Dreamworks 

    -> realized I didn’t like big companies
    Recruited a bunch senior year, failed a bunch of interviews
    Got a full time offer at a financial startup (75k) -> wasn’t really excited, but
    wanted a job
    Found an internship at a startup (7k / month)

    Converted to full time after 3 months (90k) -> got a raise after 6 months
    (100k)

    View Slide

  63. Interned at Dreamworks 

    -> realized I didn’t like big companies
    Recruited a bunch senior year, failed a bunch of interviews
    Got a full time offer at a financial startup (75k) -> wasn’t really excited, but
    wanted a job
    Found an internship at a startup (7k / month)

    Converted to full time after 3 months (90k) -> got a raise after 6 months
    (100k)
    One year later… Wanted to feel more challenged at my job -> took a
    CodePath Android class (8 weeks)

    View Slide

  64. Interned at Dreamworks 

    -> realized I didn’t like big companies
    Recruited a bunch senior year, failed a bunch of interviews
    Got a full time offer at a financial startup (75k) -> wasn’t really excited, but
    wanted a job
    Found an internship at a startup (7k / month)

    Converted to full time after 3 months (90k) -> got a raise after 6 months
    (100k)
    One year later… Wanted to feel more challenged at my job -> took a
    CodePath Android class (8 weeks)
    Recruited for Android jobs -> failed a bunch

    View Slide

  65. Got two full time offers at two different startups 

    - company A (110k)

    - company B (105k)

    - negotiated a bit: company A -> 110k, company B -> 115k + 15k sign
    on bonus

    View Slide

  66. Got two full time offers at two different startups 

    - company A (110k)

    - company B (105k)

    - negotiated a bit: company A -> 110k, company B -> 115k + 15k sign
    on bonus
    1.5 years later -> Felt like I wasn’t learning much anymore -> looked for
    jobs at hardware companies

    View Slide

  67. Got two full time offers at two different startups 

    - company A (110k)

    - company B (105k)

    - negotiated a bit: company A -> 110k, company B -> 115k + 15k sign
    on bonus
    1.5 years later -> Felt like I wasn’t learning much anymore -> looked for
    jobs at hardware companies
    2 years later -> Thought about starting to save more money -> Recruited
    at big companies

    View Slide