String Compression











up vote
1
down vote

favorite













Implement a method to perform basic string compression using the counts
of repeated characters.



For example, the string "aabcccccaaa" would become "a2b1c5a3". If the
"compressed" string would not become smaller than the original string, your method should return
the original string. You can assume the string has only uppercase and lowercase letters (a - z).




My solution is:



GitHub



public class StringCompression {

public static String compress(String input) {
if (input == null) {
return null;
}

StringBuilder output = new StringBuilder();

char prevChar = input.charAt(0);
int lengthSoFar = 1;

for (int index = 1; index < input.length(); index++) {
char currentChar = input.charAt(index);

if (prevChar == currentChar) {
lengthSoFar++;
} else {
output.append(prevChar);
output.append(lengthSoFar);

// reset counters
prevChar = currentChar;
lengthSoFar = 1;
}
}
output.append(prevChar);
output.append(lengthSoFar);

return output.toString().length() <= input.length() ? output.toString() : input;
}
}









share|improve this question






















  • i would suggest only one change, the character abbccc translates into a1b2c3 ...rather than doing this, just keep single characters directly. E.g: above string should translate to ab2c3 . Also, you are calling output.toString() twice, you can get by doing it only once.
    – akshaya pandey
    Nov 21 at 15:57

















up vote
1
down vote

favorite













Implement a method to perform basic string compression using the counts
of repeated characters.



For example, the string "aabcccccaaa" would become "a2b1c5a3". If the
"compressed" string would not become smaller than the original string, your method should return
the original string. You can assume the string has only uppercase and lowercase letters (a - z).




My solution is:



GitHub



public class StringCompression {

public static String compress(String input) {
if (input == null) {
return null;
}

StringBuilder output = new StringBuilder();

char prevChar = input.charAt(0);
int lengthSoFar = 1;

for (int index = 1; index < input.length(); index++) {
char currentChar = input.charAt(index);

if (prevChar == currentChar) {
lengthSoFar++;
} else {
output.append(prevChar);
output.append(lengthSoFar);

// reset counters
prevChar = currentChar;
lengthSoFar = 1;
}
}
output.append(prevChar);
output.append(lengthSoFar);

return output.toString().length() <= input.length() ? output.toString() : input;
}
}









share|improve this question






















  • i would suggest only one change, the character abbccc translates into a1b2c3 ...rather than doing this, just keep single characters directly. E.g: above string should translate to ab2c3 . Also, you are calling output.toString() twice, you can get by doing it only once.
    – akshaya pandey
    Nov 21 at 15:57















up vote
1
down vote

favorite









up vote
1
down vote

favorite












Implement a method to perform basic string compression using the counts
of repeated characters.



For example, the string "aabcccccaaa" would become "a2b1c5a3". If the
"compressed" string would not become smaller than the original string, your method should return
the original string. You can assume the string has only uppercase and lowercase letters (a - z).




My solution is:



GitHub



public class StringCompression {

public static String compress(String input) {
if (input == null) {
return null;
}

StringBuilder output = new StringBuilder();

char prevChar = input.charAt(0);
int lengthSoFar = 1;

for (int index = 1; index < input.length(); index++) {
char currentChar = input.charAt(index);

if (prevChar == currentChar) {
lengthSoFar++;
} else {
output.append(prevChar);
output.append(lengthSoFar);

// reset counters
prevChar = currentChar;
lengthSoFar = 1;
}
}
output.append(prevChar);
output.append(lengthSoFar);

return output.toString().length() <= input.length() ? output.toString() : input;
}
}









share|improve this question














Implement a method to perform basic string compression using the counts
of repeated characters.



For example, the string "aabcccccaaa" would become "a2b1c5a3". If the
"compressed" string would not become smaller than the original string, your method should return
the original string. You can assume the string has only uppercase and lowercase letters (a - z).




My solution is:



GitHub



public class StringCompression {

public static String compress(String input) {
if (input == null) {
return null;
}

StringBuilder output = new StringBuilder();

char prevChar = input.charAt(0);
int lengthSoFar = 1;

for (int index = 1; index < input.length(); index++) {
char currentChar = input.charAt(index);

if (prevChar == currentChar) {
lengthSoFar++;
} else {
output.append(prevChar);
output.append(lengthSoFar);

// reset counters
prevChar = currentChar;
lengthSoFar = 1;
}
}
output.append(prevChar);
output.append(lengthSoFar);

return output.toString().length() <= input.length() ? output.toString() : input;
}
}






java algorithm programming-challenge interview-questions compression






share|improve this question













share|improve this question











share|improve this question




share|improve this question










asked Nov 20 at 20:03









Exploring

21013




21013












  • i would suggest only one change, the character abbccc translates into a1b2c3 ...rather than doing this, just keep single characters directly. E.g: above string should translate to ab2c3 . Also, you are calling output.toString() twice, you can get by doing it only once.
    – akshaya pandey
    Nov 21 at 15:57




















  • i would suggest only one change, the character abbccc translates into a1b2c3 ...rather than doing this, just keep single characters directly. E.g: above string should translate to ab2c3 . Also, you are calling output.toString() twice, you can get by doing it only once.
    – akshaya pandey
    Nov 21 at 15:57


















i would suggest only one change, the character abbccc translates into a1b2c3 ...rather than doing this, just keep single characters directly. E.g: above string should translate to ab2c3 . Also, you are calling output.toString() twice, you can get by doing it only once.
– akshaya pandey
Nov 21 at 15:57






i would suggest only one change, the character abbccc translates into a1b2c3 ...rather than doing this, just keep single characters directly. E.g: above string should translate to ab2c3 . Also, you are calling output.toString() twice, you can get by doing it only once.
– akshaya pandey
Nov 21 at 15:57












2 Answers
2






active

oldest

votes

















up vote
3
down vote













For input "fooo", the implementation returns "f1o3",
which is the same length, and violates one of the requirements:




If the "compressed" string would not become smaller than the original string, your method should return the original string.




The fix is in the return statement: change <= to <.





Another corner case is when the input is empty, the statement char prevChar = input.charAt(0); will throw StringIndexOutOfBoundsException.





Lastly, a performance pitfall in the return statement,
output.toString() creates a new string,
therefore the following may result in double computation:




return output.toString().length() < input.length() ? output.toString() : input;



You could instead benefit from the length() method of StringBuilder:



return output.length() < input.length() ? output.toString() : input;





share|improve this answer




























    up vote
    1
    down vote













    Generates an out of bounds exception if passed an empty (but not null) string.



    The new StringBuilder() should be passed an initial size for the character buffer, to avoid continuous reallocations. Lacking any other reasonable value, I’d recommend passing in the original string length.



    StringBuilder output = new StringBuilder(input.length());





    share|improve this answer





















      Your Answer





      StackExchange.ifUsing("editor", function () {
      return StackExchange.using("mathjaxEditing", function () {
      StackExchange.MarkdownEditor.creationCallbacks.add(function (editor, postfix) {
      StackExchange.mathjaxEditing.prepareWmdForMathJax(editor, postfix, [["\$", "\$"]]);
      });
      });
      }, "mathjax-editing");

      StackExchange.ifUsing("editor", function () {
      StackExchange.using("externalEditor", function () {
      StackExchange.using("snippets", function () {
      StackExchange.snippets.init();
      });
      });
      }, "code-snippets");

      StackExchange.ready(function() {
      var channelOptions = {
      tags: "".split(" "),
      id: "196"
      };
      initTagRenderer("".split(" "), "".split(" "), channelOptions);

      StackExchange.using("externalEditor", function() {
      // Have to fire editor after snippets, if snippets enabled
      if (StackExchange.settings.snippets.snippetsEnabled) {
      StackExchange.using("snippets", function() {
      createEditor();
      });
      }
      else {
      createEditor();
      }
      });

      function createEditor() {
      StackExchange.prepareEditor({
      heartbeatType: 'answer',
      convertImagesToLinks: false,
      noModals: true,
      showLowRepImageUploadWarning: true,
      reputationToPostImages: null,
      bindNavPrevention: true,
      postfix: "",
      imageUploader: {
      brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
      contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
      allowUrls: true
      },
      onDemand: true,
      discardSelector: ".discard-answer"
      ,immediatelyShowMarkdownHelp:true
      });


      }
      });














       

      draft saved


      draft discarded


















      StackExchange.ready(
      function () {
      StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fcodereview.stackexchange.com%2fquestions%2f208089%2fstring-compression%23new-answer', 'question_page');
      }
      );

      Post as a guest















      Required, but never shown

























      2 Answers
      2






      active

      oldest

      votes








      2 Answers
      2






      active

      oldest

      votes









      active

      oldest

      votes






      active

      oldest

      votes








      up vote
      3
      down vote













      For input "fooo", the implementation returns "f1o3",
      which is the same length, and violates one of the requirements:




      If the "compressed" string would not become smaller than the original string, your method should return the original string.




      The fix is in the return statement: change <= to <.





      Another corner case is when the input is empty, the statement char prevChar = input.charAt(0); will throw StringIndexOutOfBoundsException.





      Lastly, a performance pitfall in the return statement,
      output.toString() creates a new string,
      therefore the following may result in double computation:




      return output.toString().length() < input.length() ? output.toString() : input;



      You could instead benefit from the length() method of StringBuilder:



      return output.length() < input.length() ? output.toString() : input;





      share|improve this answer

























        up vote
        3
        down vote













        For input "fooo", the implementation returns "f1o3",
        which is the same length, and violates one of the requirements:




        If the "compressed" string would not become smaller than the original string, your method should return the original string.




        The fix is in the return statement: change <= to <.





        Another corner case is when the input is empty, the statement char prevChar = input.charAt(0); will throw StringIndexOutOfBoundsException.





        Lastly, a performance pitfall in the return statement,
        output.toString() creates a new string,
        therefore the following may result in double computation:




        return output.toString().length() < input.length() ? output.toString() : input;



        You could instead benefit from the length() method of StringBuilder:



        return output.length() < input.length() ? output.toString() : input;





        share|improve this answer























          up vote
          3
          down vote










          up vote
          3
          down vote









          For input "fooo", the implementation returns "f1o3",
          which is the same length, and violates one of the requirements:




          If the "compressed" string would not become smaller than the original string, your method should return the original string.




          The fix is in the return statement: change <= to <.





          Another corner case is when the input is empty, the statement char prevChar = input.charAt(0); will throw StringIndexOutOfBoundsException.





          Lastly, a performance pitfall in the return statement,
          output.toString() creates a new string,
          therefore the following may result in double computation:




          return output.toString().length() < input.length() ? output.toString() : input;



          You could instead benefit from the length() method of StringBuilder:



          return output.length() < input.length() ? output.toString() : input;





          share|improve this answer












          For input "fooo", the implementation returns "f1o3",
          which is the same length, and violates one of the requirements:




          If the "compressed" string would not become smaller than the original string, your method should return the original string.




          The fix is in the return statement: change <= to <.





          Another corner case is when the input is empty, the statement char prevChar = input.charAt(0); will throw StringIndexOutOfBoundsException.





          Lastly, a performance pitfall in the return statement,
          output.toString() creates a new string,
          therefore the following may result in double computation:




          return output.toString().length() < input.length() ? output.toString() : input;



          You could instead benefit from the length() method of StringBuilder:



          return output.length() < input.length() ? output.toString() : input;






          share|improve this answer












          share|improve this answer



          share|improve this answer










          answered Nov 20 at 21:34









          janos

          96.6k12124350




          96.6k12124350
























              up vote
              1
              down vote













              Generates an out of bounds exception if passed an empty (but not null) string.



              The new StringBuilder() should be passed an initial size for the character buffer, to avoid continuous reallocations. Lacking any other reasonable value, I’d recommend passing in the original string length.



              StringBuilder output = new StringBuilder(input.length());





              share|improve this answer

























                up vote
                1
                down vote













                Generates an out of bounds exception if passed an empty (but not null) string.



                The new StringBuilder() should be passed an initial size for the character buffer, to avoid continuous reallocations. Lacking any other reasonable value, I’d recommend passing in the original string length.



                StringBuilder output = new StringBuilder(input.length());





                share|improve this answer























                  up vote
                  1
                  down vote










                  up vote
                  1
                  down vote









                  Generates an out of bounds exception if passed an empty (but not null) string.



                  The new StringBuilder() should be passed an initial size for the character buffer, to avoid continuous reallocations. Lacking any other reasonable value, I’d recommend passing in the original string length.



                  StringBuilder output = new StringBuilder(input.length());





                  share|improve this answer












                  Generates an out of bounds exception if passed an empty (but not null) string.



                  The new StringBuilder() should be passed an initial size for the character buffer, to avoid continuous reallocations. Lacking any other reasonable value, I’d recommend passing in the original string length.



                  StringBuilder output = new StringBuilder(input.length());






                  share|improve this answer












                  share|improve this answer



                  share|improve this answer










                  answered Nov 20 at 21:38









                  AJNeufeld

                  3,785317




                  3,785317






























                       

                      draft saved


                      draft discarded



















































                       


                      draft saved


                      draft discarded














                      StackExchange.ready(
                      function () {
                      StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fcodereview.stackexchange.com%2fquestions%2f208089%2fstring-compression%23new-answer', 'question_page');
                      }
                      );

                      Post as a guest















                      Required, but never shown





















































                      Required, but never shown














                      Required, but never shown












                      Required, but never shown







                      Required, but never shown

































                      Required, but never shown














                      Required, but never shown












                      Required, but never shown







                      Required, but never shown







                      Popular posts from this blog

                      Сан-Квентин

                      Алькесар

                      Josef Freinademetz