Fill strings with 0's using formatter - java

I know I can fill with spaces using :
String.format("%6s", "abc"); // ___abc ( three spaces before abc
But I can't seem to find how to produce:
000abc
Edit:
I tried %06s prior to asking this. Just letting you know before more ( untried ) answers show up.
Currently I have: String.format("%6s", data ).replace(' ', '0' ) But I think there must exists a better way.

You should really consider using StringUtils from Apache Commons Lang for such String manipulation tasks as your code will get much more readable. Your example would be StringUtils.leftPad("abc", 6, ' ');

Try rolling your own static-utility method
public static String leftPadStringWithChar(String s, int fixedLength, char c){
if(fixedLength < s.length()){
throw new IllegalArgumentException();
}
StringBuilder sb = new StringBuilder(s);
for(int i = 0; i < fixedLength - s.length(); i++){
sb.insert(0, c);
}
return sb.toString();
}
And then use it, as such
System.out.println(leftPadStringWithChar("abc", 6, '0'));
OUTPUT
000abc

By all means, find a library you like for this kind of stuff and learn what's in your shiny new toolbox so you reinvent fewer wheels (that sometimes have flats). I prefer Guava to Apache Commons. In this case they are equivalent:
Strings.padStart("abc",6,'0');

Quick and dirty (set the length of the "000....00" string as the maximum len you support) :
public static String lefTpadWithZeros(String x,int minlen) {
return x.length()<minlen ?
"000000000000000".substring(0,minlen-x.length()) + x : x;
}

I think this is what you're looking for.
String.format("%06s", "abc");

Related

How to join Array to String (Java)?

Let's assume there is an array:
String[] myArray = new String[]{"slim cat", "fat cat", "extremely fat cat"};
Now I want to transform this array into String with tokens "&", which value is:
slim cat&fat cat&extremely fat cat
How can I achieve this without using for loop? I mean the simplest solution, like we used to to in reverse way like someString.split();
Using Java 8:
String result = String.join("&", myArray);
Using Java 7 or earlier, you either need a loop or recursion.
Use guava's Joiner or java 8 StringJoiner.
Edit: Why without a for loop?
Use a StringBuilder
StringBuilder builder = new StringBuilder();
builder.append( myArray.remove(0));
for( String s : myArray) {
builder.append( "&");
builder.append( s);
}
String result = builder.toString();
You might use Arrays.toString(Object[]) and rewrite the result. Something like,
String[] myArray = { "slim cat", "fat cat", "extremely fat cat" };
String str = Arrays.toString(myArray).replace(", ", "&");
str = str.substring(1, str.length() - 1);
System.out.println(str);
Output is (as requested)
slim cat&fat cat&extremely fat cat
Note, this only works if there are no ", " in your inputs (as is the case here).
There's no way to do this job without some sort of iteration over the array. Even languages that offer some form of a join() function (which do not include Java < version 8) must internally perform some sort of iteration.
About the simplest way to do it in Java <= 7 is this:
StringBuilder sb = new StringBuilder();
String result;
for (String s : myArray) {
sb.append(s).append('&');
}
sb.deleteCharAt(sb.length() - 1);
result = sb.toString();
Please, take a look at http://commons.apache.org/proper/commons-lang/javadocs/api-2.6/org/apache/commons/lang/StringUtils.html#join(java.lang.Object[], char). This library is compatible with a lot of version of JDK and, as you can see, you have a lot of overridden methods.

regular expression replace 2 characters with one

i would like to use a regular expression for the following problem:
SOME_RANDOM_TEXT
should be converted to:
someRandomText
so, the _(any char) should be replaced with just the letter in upper case. i found something like that, using the tool:
_\w and $&
how to get only the second letter from the replacement?? any advice? thanks.
It might be easier simply to String.split("_") and then rejoin, capitalising the first letter of each string in your collection.
Note that Apache Commons has lots of useful string-related stuff, including a join() method.
The problem is that the case conversion from lowercase to uppercase is not supported by Java.util.regex.Pattern
This means you will need to do the conversion programmatically as Brian suggested. See also this thread
You can also write a simple method to do this. It's more complicated but more optimized :
public static String toCamelCase(String value) {
value = value.toLowerCase();
byte[] source = value.getBytes();
int maxLen = source.length;
byte[] target = new byte[maxLen];
int targetIndex = 0;
for (int sourceIndex = 0; sourceIndex < maxLen; sourceIndex++) {
byte c = source[sourceIndex];
if (c == '_') {
if (sourceIndex < maxLen - 1)
source[sourceIndex + 1] = (byte) Character.toUpperCase(source[sourceIndex + 1]);
continue;
}
target[targetIndex++] = source[sourceIndex];
}
return new String(target, 0, targetIndex);
}
I like Apache commons libraries, but sometimes it's good to know how it works and be able to write some specific code for jobs like this.

Most efficient way to fill a String with a specified length with a specified character?

Basically given an int, I need to generate a String with the same length containing only the specified character. Related question here, but it relates to C# and it does matter what's in the String.
This question, and my answer to it are why I am asking this one. I'm not sure what's the best way to go about it performance wise.
Example
Method signature:
String getPattern(int length, char character);
Usage:
//returns "zzzzzz"
getPattern(6, 'z');
What I've tried
String getPattern(int length, char character) {
String result = "";
for (int i = 0; i < length; i++) {
result += character;
}
return result;
}
Is this the best that I can do performance-wise?
You should use StringBuilder instead of concatenating chars this way. Use StringBuilder.append().
StringBuilder will give you better performance. The problem with concatenation the way you are doing is each time a new String (string is immutable) is created then the old string is copied, the new string is appended, and the old String is thrown away. It's a lot of extra work that over a period of type (like in a big for loop) will cause performance degradation.
StringUtils from commons-lang or Strings from guava are your friends. As already stated avoid String concatenations.
StringUtils.repeat("a", 3) // => "aaa"
Strings.repeat("hey", 3) // => "heyheyhey"
Use primitive char arrays & some standard util classes like Arrays
public class Test {
static String getPattern(int length, char character) {
char[] cArray = new char[length];
Arrays.fill(cArray, character);
// return Arrays.toString(cArray);
return new String(cArray);
}
static String buildPattern(int length, char character) {
StringBuilder sb= new StringBuilder(length);
for (int i = 0; i < length; i++) {
sb.append(character);
}
return sb.toString();
}
public static void main(String args[]){
long time = System.currentTimeMillis();
getPattern(10000000,'c');
time = System.currentTimeMillis() - time;
System.out.println(time); //prints 93
time = System.currentTimeMillis();
buildPattern(10000000,'c');
time = System.currentTimeMillis() - time;
System.out.println(time); //prints 188
}
}
EDIT Arrays.toString() gave lower performance since it eventually used a StringBuilder, but the new String did the magic.
Yikes, no.
A String is immutable in java; you can't change it. When you say:
result += character;
You're creating a new String every time.
You want to use a StringBuilder and append to it, then return a String with its toString() method.
I think it would be more efficient to do it like following,
String getPattern(int length, char character)
{
char[] list = new char[length];
for(int i =0;i<length;i++)
{
list[i] = character;
}
return new string(list);
}
Concatenating a String is never the most efficient, since String is immutable, for better performance you should use StringBuilder, and append()
String getPattern(int length, char character) {
StringBuilder sb= new StringBuilder(length)
for (int i = 0; i < length; i++) {
sb.append(character);
}
return sb.toString();
}
Performance-wise, I think you'd have better results creating a small String and concatenating (using StringBuilder of course) until you reach the request size: concatenating/appending "zzz" to "zzz" performs probably betters than concatenating 'z' three times (well, maybe not for such small numbers, but when you reach 100 or so chars, doing ten concatenations of 'z' followed by ten concatenations of "zzzzzzzzzz" is probably better than 100 concatenatinos of 'z').
Also, because you ask about GWT, results will vary a lot between DevMode (pure Java) and "production mode" (running in JS in the browser), and is likely to vary depending on the browser.
The only way to really know is to benchmark, everything else is pure speculation.
And possibly use deferred binding to use the most performing variant in each browser (that's exactly how StringBuilder is emulated in GWT).

Is there an equivalent of ucwords in java

In php, the method ucwords converts any string in a string where each words first character is in uppercase, and all other characters are lower case.
I always end up making my own implementation, and I'm wondering if a standard method exists.
That's called capitalization. Use Apache Commons's StringUtils to do that.
See more here:
http://commons.apache.org/proper/commons-lang/apidocs/org/apache/commons/lang3/StringUtils.html
WordUtils is also worth looking at. See here
Otherwise it's a rather simple fix such as; String string1 = someString.substring(0,1).toUpperCase() + someString.substring(1);
You can put it in a function, and call it whenever you need. Saves you the trouble of maintaining libraries you don't need. (not that apache commons is ever trouble, but you get the point..)
EDIT: someString.substring(1) part can be written as someString.substring(1).toLowerCase() just to make sure that the rest of the string is in lowercase
I don't know about any direct equivalent, but you can always write one:
public static String capitalize(String input) {
if (input == null || input.length() <= 0) {
return input;
}
char[] chars = new char[1];
input.getChars(0, 1, chars, 0);
if (Character.isUpperCase(chars[0])) {
return input;
} else {
StringBuilder buffer = new StringBuilder(input.length());
buffer.append(Character.toUpperCase(chars[0]));
buffer.append(input.toCharArray(), 1, input.length()-1);
return buffer.toString();
}
}

How do I get the first n characters of a string without checking the size or going out of bounds?

How do I get up to the first n characters of a string in Java without doing a size check first (inline is acceptable) or risking an IndexOutOfBoundsException?
Here's a neat solution:
String upToNCharacters = s.substring(0, Math.min(s.length(), n));
Opinion: while this solution is "neat", I think it is actually less readable than a solution that uses if / else in the obvious way. If the reader hasn't seen this trick, he/she has to think harder to understand the code. IMO, the code's meaning is more obvious in the if / else version. For a cleaner / more readable solution, see #paxdiablo's answer.
Don't reinvent the wheel...:
org.apache.commons.lang.StringUtils.substring(String s, int start, int len)
Javadoc says:
StringUtils.substring(null, *, *) = null
StringUtils.substring("", * , *) = "";
StringUtils.substring("abc", 0, 2) = "ab"
StringUtils.substring("abc", 2, 0) = ""
StringUtils.substring("abc", 2, 4) = "c"
StringUtils.substring("abc", 4, 6) = ""
StringUtils.substring("abc", 2, 2) = ""
StringUtils.substring("abc", -2, -1) = "b"
StringUtils.substring("abc", -4, 2) = "ab"
Thus:
StringUtils.substring("abc", 0, 4) = "abc"
Apache Commons Lang has a StringUtils.left method for this.
String upToNCharacters = StringUtils.left(s, n);
String upToNCharacters = String.format("%."+ n +"s", str);
Awful if n is a variable (so you must construct the format string), but pretty clear if a constant:
String upToNCharacters = String.format("%.10s", str);
docs
There's a class of question on SO that sometimes make less than perfect sense, this one is perilously close :-)
Perhaps you could explain your aversion to using one of the two methods you ruled out.
If it's just because you don't want to pepper your code with if statements or exception catching code, one solution is to use a helper function that will take care of it for you, something like:
static String substring_safe (String s, int start, int len) { ... }
which will check lengths beforehand and act accordingly (either return smaller string or pad with spaces).
Then you don't have to worry about it in your code at all, just call:
String s2 = substring_safe (s, 10, 7);
instead of:
String s2 = s.substring (10,7);
This would work in the case that you seem to be worried about (based on your comments to other answers), not breaking the flow of the code when doing lots of string building stuff.
Use the substring method, as follows:
int n = 8;
String s = "Hello, World!";
System.out.println(s.substring(0,n);
If n is greater than the length of the string, this will throw an exception, as one commenter has pointed out. one simple solution is to wrap all this in the condition if(s.length()<n) in your else clause, you can choose whether you just want to print/return the whole String or handle it another way.
ApacheCommons surprised me,
StringUtils.abbreviate(String str, int maxWidth) appends "..." there is no option to change postfix.
WordUtils.abbreviate(String str, int lower, int upper, String appendToEnd) looks up to next empty space.
I’m just going to leave this here:
public static String abbreviate(String s, int maxLength, String appendToEnd) {
String result = s;
appendToEnd = appendToEnd == null ? "" : appendToEnd;
if (maxLength >= appendToEnd.length()) {
if (s.length()>maxLength) {
result = s.substring(0, Math.min(s.length(), maxLength - appendToEnd.length())) + appendToEnd;
}
} else {
throw new StringIndexOutOfBoundsException("maxLength can not be smaller than appendToEnd parameter length.");
}
return result;
}

Categories