{"id":2041,"date":"2024-03-01T12:00:00","date_gmt":"2024-03-01T12:00:00","guid":{"rendered":"https:\/\/favtutor.com\/articles\/?p=2041"},"modified":"2024-03-02T10:27:04","modified_gmt":"2024-03-02T10:27:04","slug":"edit-distance-problem","status":"publish","type":"post","link":"https:\/\/favtutor.com\/articles\/edit-distance-problem\/","title":{"rendered":"Edit Distance Problem (C++, Java, Python)"},"content":{"rendered":"\n<p>Dynamic programming is the most important topic in DSA, often asked in most technical interviews. It helps us reduce time complexity by storing previously computed values and using them whenever needed. In this article, we will discuss the problem of &#8220;Edit Distance,&#8221; which can be solved by using dynamic programming.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\"><strong>Edit Distance Problem Explained<\/strong><\/h2>\n\n\n\n<p><strong>In the Edit Distance problem, you are given two strings: string s1 and string s2. You must find out how many minimum numbers of operations are required such that string s1 is converted to string s2. <\/strong><\/p>\n\n\n\n<p>There are 3 different types of operations you can perform on s1.<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li>Insert a character.<\/li>\n\n\n\n<li>Erase a character.<\/li>\n\n\n\n<li>Replace a character.<\/li>\n<\/ul>\n\n\n\n<p>For example, if you are given the string s1 = \u201cfovutyor\u201d and the string s2 = \u201cfavtutor,\u201d you need a minimum of 3 characters to convert s1 to s2. <\/p>\n\n\n\n<p>First, you use the replace character operation to replace \u2018o\u2019 with \u2018a\u2019; now the string becomes \u201cfavutyor.\u201d Second, you use the insert operation to insert &#8216;t&#8217; at index 4; now the string becomes \u201cfavtutyor.\u201d At last, you use the erase operation to remove &#8216;y&#8217;. Now the string s1 is converted to s2.<\/p>\n\n\n\n<figure class=\"wp-block-image\"><img decoding=\"async\" src=\"https:\/\/lh7-us.googleusercontent.com\/zY2soboav1KfF6VLJmZhA-fv-uP89JZoSl7b4NlEZRsO313tI438D8bHSES5P55kEQTgs7tu7hKKzVvrQHURjQ5u_hsGvAvermJ3RI4wbgW105RUeSm-z0yGjClXi2jVJOYB83kFoSk12kmetzqKVb0\" alt=\"Example of Edit Distance problem\"\/><\/figure>\n\n\n\n<figure class=\"wp-block-image\"><img decoding=\"async\" src=\"https:\/\/lh7-us.googleusercontent.com\/nN_yzHM8JNCAdPstSsDd8r8aqV1QTO8zIiG8GLbIwNwVwgMwElJ74Rsj9tuYBP0IjyrMDfZi7m0WC5giS-gZKWP5bRZzy9DLulxCMKjIf8YBma5tWwu0zfuv_mAPdMit9E7ww0GCAFy-ZacZnjljxnQ\" alt=\"Replace Operation\"\/><\/figure>\n\n\n\n<figure class=\"wp-block-image\"><img decoding=\"async\" src=\"https:\/\/lh7-us.googleusercontent.com\/rCHegqODbpAcPnjcQ1I3Nv-Ql1KuSH-CLguFv92z-fx1ksVc4_Ob-1U3hf8e7cr-BSGgFeiE7zFNI6sv8BMgJm0yV3sdHL9tyZ5kQr_2m5sQ9ikmRl2xKmUbPeZdsd40lYKJXaLdqONpO3PX7HDm7HI\" alt=\"Insert Operation\"\/><\/figure>\n\n\n\n<figure class=\"wp-block-image\"><img decoding=\"async\" src=\"https:\/\/lh7-us.googleusercontent.com\/unq-1wurUdwyCuYl_TaNE0HtqvPxseJ7QRne4glSKyf0jSKJ70FRNNYSHNavqr-PJwXIFwODDKTEqyHXb9ofWG9QpYAaWM7g7vZcGTXdPK5PLv-eNcNB-NKsfDnnnuLr2e5TZSZkm9a41Eorwyx2rmo\" alt=\"Delete Operation\"\/><\/figure>\n\n\n\n<h2 class=\"wp-block-heading\"><strong>Brute Force Approach<\/strong><\/h2>\n\n\n\n<p>The naive way is to look at all the possible ways in which we can convert the string s1 to string s2 and find the one that takes a minimum number of operations. This can be done if we go to each index and perform all the tree operations i.e. insert, erase, and replace one by one, find the minimum among them, and return the answer.<\/p>\n\n\n\n<p>Let\u2019s find out how to do it step-by-step:<\/p>\n\n\n\n<ol class=\"wp-block-list\">\n<li>First, create a function that will return the minimum operations needed to convert string s1 to s2.<\/li>\n\n\n\n<li>Now send the current index of strings s1 and s2 at first they both are 0.<\/li>\n\n\n\n<li>Now check if any of the indexes have the same value as the size of their string.<\/li>\n\n\n\n<li>If not, return the sum of the difference between both strings with their current index.<\/li>\n\n\n\n<li>If not. check if the characters of both strings are the same at the given indexes.<\/li>\n\n\n\n<li>If not, return the 1 + minimum value among all three operations.<\/li>\n<\/ol>\n\n\n\n<p>The time complexity of the above solution is O(3^n) where n is the size of string s1. As at each index, we are performing 3 operations remove, replace, and delete which are laid to O(3^n) time complexity. The space complexity for the above code is O(1).<\/p>\n\n\n\n<h2 class=\"wp-block-heading\"><strong>Dynamic Programming Approach<\/strong><\/h2>\n\n\n\n<p>In the above approach, we observe that we are computing the minimum operations by performing all three operations on each index. This leads to a high time complexity as we might compute the same values repeatedly. Therefore, instead of computing the same values, we will store them in an array and then determine the minimum operations.<\/p>\n\n\n\n<p>Let us examine how we can convert the above approach into a memorized one:<\/p>\n\n\n\n<ol class=\"wp-block-list\">\n<li>Create an array of size n*m where n is the size of string s1 and m is the size of s2.<\/li>\n\n\n\n<li>Now initialize all the values in the array with -1.<\/li>\n\n\n\n<li>Now, whenever you are computing any value, check if the array value at that index is -1 or not.<\/li>\n\n\n\n<li>If not return the value which is stored in the array.<\/li>\n\n\n\n<li>Otherwise, compute the value and store it in the array.<\/li>\n<\/ol>\n\n\n\n<p>The time complexity of the above solution is O(n*m) where n is the size of string s1 and m is the size of s2. At each index, we are performing 3 operations remove, replace, and delete, and also storing those values into the array. The space complexity for the above code is O(n*m) as we are making the array to store the repeating values.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\"><strong>Space Optimized Approach<\/strong><\/h2>\n\n\n\n<p>In the above approach, we are consuming <strong>O(n*m) <\/strong>space which can be reduced if we store the previously computed values instead of storing all the values. Let\u2019s examine this approach step by step.<\/p>\n\n\n\n<ol class=\"wp-block-list\">\n<li>First, create two arrays prv and curr of size n+1 where n is the size of s1. Initialize all the values of the array with 0.<\/li>\n\n\n\n<li>When the size of string 2 is 0. Then number of operations required is equal to the size of string s1.<\/li>\n\n\n\n<li>When the size of string 1 is 0. Then number of operations required is equal to the size of string s2.<\/li>\n\n\n\n<li>If both the characters are the same at given indexes then move forward by assigning the previous value.<\/li>\n\n\n\n<li>If not find all the possible operations we can do.<\/li>\n<\/ol>\n\n\n\n<p>Let\u2019s examine the code for the above process.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\"><strong>C++ Code<\/strong><\/h3>\n\n\n\n<p>We can implement this approach in C++ to solve the Edit Distance problem:<\/p>\n\n\n\n<div class=\"wp-block-codemirror-blocks-code-block code-block\"><pre class=\"CodeMirror\" data-setting=\"{&quot;mode&quot;:&quot;clike&quot;,&quot;mime&quot;:&quot;text\/x-c++src&quot;,&quot;theme&quot;:&quot;material&quot;,&quot;lineNumbers&quot;:true,&quot;styleActiveLine&quot;:false,&quot;lineWrapping&quot;:false,&quot;readOnly&quot;:true,&quot;language&quot;:&quot;C++&quot;,&quot;modeName&quot;:&quot;cpp&quot;}\">#include&lt;bits\/stdc++.h&gt;\nusing namespace std;\n\n    int minDistance(string s1, string s2) {\n    \n        int n = s1.size(), m = s2.size();\n        vector&lt;int&gt;prv(m+2,0);\n        vector&lt;int&gt;curr(m+2,0);\n        for(int i=0; i&lt;=n; i++){\n            for(int j=0; j&lt;=m; j++){\n\n                if(i == 0){\n                    curr[j] = j;\n                }\n                else if( j == 0 ){\n                    curr[j] = i;\n                }\n                else if (s1[i-1] == s2[j-1]){\n                    curr[j] = prv[j-1];\n                }\n                else{\n                    curr[j] = 1 + min({ curr[j-1], prv[j-1], prv[j] });\n                }\n            }\n            prv = curr;\n        }\n\n        return curr[m];\n    }\n    \n\n    int main(){\n        string s1 = &quot;fovutyor&quot;, s2 =&quot;favtutor&quot;;\n        int min_operations = minDistance(s1, s2);\n        cout&lt;&lt;min_operations&lt;&lt;endl;\n        return 0;\n    }<\/pre><\/div>\n\n\n\n<h3 class=\"wp-block-heading\"><strong>Java Code<\/strong><\/h3>\n\n\n\n<p>Here is the Java code to do it:<\/p>\n\n\n\n<div class=\"wp-block-codemirror-blocks-code-block code-block\"><pre class=\"CodeMirror\" data-setting=\"{&quot;mode&quot;:&quot;clike&quot;,&quot;mime&quot;:&quot;text\/x-java&quot;,&quot;theme&quot;:&quot;material&quot;,&quot;lineNumbers&quot;:true,&quot;styleActiveLine&quot;:false,&quot;lineWrapping&quot;:false,&quot;readOnly&quot;:true,&quot;language&quot;:&quot;Java&quot;,&quot;modeName&quot;:&quot;java&quot;}\">import java.util.Arrays;\n\nclass EditDistance {\n    public static int minDistance(String s1, String s2) {\n        int n = s1.length(), m = s2.length();\n        int[] prv = new int[m+2];\n        int[] curr = new int[m+2];\n        \n        for(int i = 0; i &lt;= n; i++) {\n            for(int j = 0; j &lt;= m; j++) {\n                if(i == 0) {\n                    curr[j] = j;\n                } else if(j == 0) {\n                    curr[j] = i;\n                } else if(s1.charAt(i-1) == s2.charAt(j-1)) {\n                    curr[j] = prv[j-1];\n                } else {\n                    curr[j] = 1 + Math.min(Math.min(curr[j-1], prv[j-1]), prv[j]);\n                }\n            }\n            prv = Arrays.copyOf(curr, curr.length);\n        }\n        \n        return curr[m];\n    }\n\n    public static void main(String[] args) {\n        String s1 = &quot;fovutyor&quot;;\n        String s2 = &quot;favtutor&quot;;\n        int min_operations = minDistance(s1, s2);\n        System.out.println(min_operations);\n    }\n}<\/pre><\/div>\n\n\n\n<h3 class=\"wp-block-heading\"><strong>Python Code<\/strong><\/h3>\n\n\n\n<p>You can also use Python to implement it:<\/p>\n\n\n\n<div class=\"wp-block-codemirror-blocks-code-block code-block\"><pre class=\"CodeMirror\" data-setting=\"{&quot;mode&quot;:&quot;python&quot;,&quot;mime&quot;:&quot;text\/x-python&quot;,&quot;theme&quot;:&quot;material&quot;,&quot;lineNumbers&quot;:true,&quot;styleActiveLine&quot;:false,&quot;lineWrapping&quot;:false,&quot;readOnly&quot;:true,&quot;language&quot;:&quot;Python&quot;,&quot;modeName&quot;:&quot;python&quot;}\">def minDistance(s1: str, s2: str) -&gt; int:\n    n = len(s1)\n    m = len(s2)\n    prv = [0] * (m + 2)\n    curr = [0] * (m + 2)\n    \n    for i in range(n + 1):\n        for j in range(m + 1):\n            if i == 0:\n                curr[j] = j\n            elif j == 0:\n                curr[j] = i\n            elif s1[i - 1] == s2[j - 1]:\n                curr[j] = prv[j - 1]\n            else:\n                curr[j] = 1 + min(curr[j - 1], prv[j - 1], prv[j])\n        prv = curr[:]\n    \n    return curr[m]\n\nif __name__ == &quot;__main__&quot;:\n    s1 = &quot;fovutyor&quot;\n    s2 = &quot;favtutor&quot;\n    min_operations = minDistance(s1, s2)\n    print(min_operations)<\/pre><\/div>\n\n\n\n<p><strong>Output:<\/strong>&nbsp;<\/p>\n\n\n\n<pre class=\"wp-block-code has-black-color has-text-color has-background has-link-color wp-elements-b4a34b2b19b7e50b8a9af62acab121a4\" style=\"background-color:#fedcba\"><code>3<\/code><\/pre>\n\n\n\n<p>The time complexity for the above process is O(n*m) as we have two nested loops to check at all the indexes. The space complexity is reduced to O(n) as we are storing the previous value and using it whenever needed.<\/p>\n\n\n\n<p>Here is a comparison of all the approaches:<\/p>\n\n\n\n<figure class=\"wp-block-table\"><table><thead><tr><th class=\"has-text-align-left\" data-align=\"left\"><strong>Approach<\/strong><\/th><th class=\"has-text-align-center\" data-align=\"center\"><strong>Time Complexity<\/strong><\/th><th class=\"has-text-align-center\" data-align=\"center\"><strong>Space Complexity<\/strong><\/th><th><strong>Description<\/strong><\/th><\/tr><\/thead><tbody><tr><td class=\"has-text-align-left\" data-align=\"left\">Brute Force&nbsp;<\/td><td class=\"has-text-align-center\" data-align=\"center\">O(3^n)<\/td><td class=\"has-text-align-center\" data-align=\"center\">O(1)<\/td><td>In this, we are checking all the possible operations and finding the minimum among them.<\/td><\/tr><tr><td class=\"has-text-align-left\" data-align=\"left\">Optimized Approach<\/td><td class=\"has-text-align-center\" data-align=\"center\">O(n*m)<\/td><td class=\"has-text-align-center\" data-align=\"center\">O(n*m)<\/td><td>We are now storing the repeated values in the above approach reducing time complexity to O(n*m)<\/td><\/tr><tr><td class=\"has-text-align-left\" data-align=\"left\">Space Optimized Approach<\/td><td class=\"has-text-align-center\" data-align=\"center\">O(n*m)<\/td><td class=\"has-text-align-center\" data-align=\"center\">O(n)<\/td><td>Here we are doing a tabulation approach and then storing only the previous values which had reduced our space.<\/td><\/tr><\/tbody><\/table><\/figure>\n\n\n\n<h2 class=\"wp-block-heading\"><strong>Conclusion<\/strong><\/h2>\n\n\n\n<p>In this article, we see how can we use <a href=\"https:\/\/favtutor.com\/blogs\/dynamic-programming\">dynamic programming<\/a> to solve the Edit Distance problem from <a href=\"https:\/\/leetcode.com\/problems\/edit-distance\/\" target=\"_blank\" rel=\"noreferrer noopener nofollow\">leetcode<\/a>. This reduces our time and space complexity. Dynamic programming is one of the most important topics in DSA that\u2019s why it is asked in most of the interviews.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Understand the Edit Distance Problem and how to solve it using dynamic programming and a space-optimized approach.<\/p>\n","protected":false},"author":14,"featured_media":2043,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"jnews-multi-image_gallery":[],"jnews_single_post":null,"jnews_primary_category":{"id":"","hide":""},"footnotes":""},"categories":[7],"tags":[14,15],"class_list":["post-2041","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-data-structures-algorithms","tag-dsa","tag-leetcode"],"_links":{"self":[{"href":"https:\/\/favtutor.com\/articles\/wp-json\/wp\/v2\/posts\/2041","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/favtutor.com\/articles\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/favtutor.com\/articles\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/favtutor.com\/articles\/wp-json\/wp\/v2\/users\/14"}],"replies":[{"embeddable":true,"href":"https:\/\/favtutor.com\/articles\/wp-json\/wp\/v2\/comments?post=2041"}],"version-history":[{"count":3,"href":"https:\/\/favtutor.com\/articles\/wp-json\/wp\/v2\/posts\/2041\/revisions"}],"predecessor-version":[{"id":2124,"href":"https:\/\/favtutor.com\/articles\/wp-json\/wp\/v2\/posts\/2041\/revisions\/2124"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/favtutor.com\/articles\/wp-json\/wp\/v2\/media\/2043"}],"wp:attachment":[{"href":"https:\/\/favtutor.com\/articles\/wp-json\/wp\/v2\/media?parent=2041"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/favtutor.com\/articles\/wp-json\/wp\/v2\/categories?post=2041"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/favtutor.com\/articles\/wp-json\/wp\/v2\/tags?post=2041"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}