I have a string apple I want it maximum 8 character long.
So i have apple. its 5 chars long. I pad it with 3* to make it ***apple
So i have bat. its 3 chars long. I pad it with 5* to make it *****bat
Is there any way to do it? Cant find any padding library out there.
Other way how you can do it:
String.format("%8s", "helllo").replace(' ', '*');
In this case you do not need to add library.
tl;dr
Built into Java 11+
"*" // A single-character string.
.repeat( 8 - "apple".length ) // `String::repeat` multiplies text. Here we return a `String` of a certain number of asterisks.
.concat( "apple" ) ; // Appends to those asterisks our original input.
***apple
String::repeat
Java 11 brought a new method, repeat, to the String class. This method multiplies a piece of text a certain number of times. Multiplying by zero is valid, resulting in an empty string.
In our case, we want to multiply a single character string, *.
int goal = 8 ;
String input = "apple" ;
int length = input.length() ;
String output = "*".repeat( goal - length ).concat( input ) ;
See this code run live at IdeOne.com.
***apple
No library needed. Uses a StringBuilder and reverse() for speed (insert is slower than append):
public String padWord(String word)
{
if(word.length() < 8)
{
StringBuilder foo = new StringBuilder(word);
foo = foo.reverse();
for(int x = word.length(); x < 8; x++)
{
foo.append('*');
}
foo.reverse();
}
return foo.toString();
}
You can use StringUtils.leftPad from Apache Commons Lang library
StringUtils.leftPad(null, *, *) = null
StringUtils.leftPad("", 3, 'z') = "zzz"
StringUtils.leftPad("bat", 3, 'z') = "bat"
StringUtils.leftPad("bat", 5, 'z') = "zzbat"
StringUtils.leftPad("bat", 1, 'z') = "bat"
StringUtils.leftPad("bat", -1, 'z') = "bat"
Related
static String clean(String identifier) {
String firstString = "";
for (int i = 0; i < identifier.length(); i++)
if (Character.isISOControl(identifier.charAt(i))){
firstString = identifier.replaceAll(identifier.charAt(i),
"CTRL");
}
return firstString;
}
The logic behind the code above is to replace all instances of ISO Control characters in the string 'identifier' with "CTRL". I'm however faced with this error: "char cannot be converted to java.lang.String"
Can someone help me to solve and improve my code to produce the right output?
String#replaceAll expects a String as parameter, but it has to be a regular expression. Use String#replace instead.
EDIT: I haven't seen that you want to replace a character by some string. In that case, you can use this version of String#replace but you need to convert the character to a String, e. g. by using Character.toString.
Update
Example:
String text = "AB\003DE";
text = text.replace(Character.toString('\003'), "CTRL");
System.out.println(text);
// gives: ABCTRLDE
Code points, and Control Picture characters
I can add two points:
The char type is essentially broken since Java 2, and legacy since Java 5. Best to use code point integers when working with individual characters.
Unicode defines characters for display as placeholders for control characters. See Control Pictures section of one Wikipedia page, and see another page, Control Pictures.
For example, the NULL character at code point 0 decimal has a matching SYMBOL FOR NULL character at 9,216 decimal: ␀. To see all the Control Picture characters, use this PDF section of the Unicode standard specification.
Get an array of the code point integers representing each of the characters in your string.
int[] codePoints = myString.codePoints().toArray() ;
Loop those code points. Replace those of interest.
Here is some untested code.
int[] replacedCodePoints = new int[ codePoints.length ] ;
int index = 0 ;
for ( int codePoint : codePoints )
{
if( codePoint >= 0 && codePoint <= 32 ) // 32 is SPACE, so you may want to use 31 depending on your context.
{
replacedCodePoints[ index ] = codePoint + 9_216 ; // 9,216 is the offset to the beginning of the Control Picture character range defined in Unicode.
} else if ( codePoint == 127 ) // DEL character.
{
replacedCodePoints[ index ] = 9_249 ;
} else // Any other character, we keep as-is, no replacement.
{
replacedCodePoints[ index ] = codePoint ;
}
i ++ ; // Set up the next loop.
}
Convert code points back into text. Use StringBuilder#appendCodePoint to build up the characters of text. You can use the following stream-based code as boilerplate. For explanation, see this Question.
String result =
Arrays
.stream( replacedCodePoints )
.collect( StringBuilder::new , StringBuilder::appendCodePoint , StringBuilder::append )
.toString();
Recently, only I notice that, it is possible for substring to return string with invalid unicode character.
For instance
public class Main {
public static void main(String[] args) {
String text = "🥦_Salade verte";
/* We should avoid using endIndex = 1, as it will cause an invalid character in the returned substring. */
// 1 : ?
System.out.println("1 : " + text.substring(0, 1));
// 2 : 🥦
System.out.println("2 : " + text.substring(0, 2));
// 3 : 🥦_
System.out.println("3 : " + text.substring(0, 3));
// 4 : 🥦_S
System.out.println("4 : " + text.substring(0, 4));
}
}
I was wondering, when trimming a long string with String.substring, what are some good ways to avoid the returned substring from containing invalid unicode?
char obsolete
The char type has been legacy since Java 2, essentially broken. As a 16-bit value, char is physically incapable of representing most characters.
Your discovery suggests that the String#substring command is char based. Hence the problem shown in your code.
Code point
Instead, use code point integer numbers when working with individual characters.
int[] codePoints = "🥦_Salade".codePoints().toArray() ;
[129382, 95, 83, 97, 108, 97, 100, 101]
Extract the first character’s code point.
int codePoint = codePoints[ 0 ] ;
129382
Make a single-character String object for that code point.
String firstCharacter = Character.toString( codePoint ) ;
🥦
You can grab a subset of that int array of code points.
int[] firstFewCodePoints = Arrays.copyOfRange( codePoints , 0 , 3 ) ;
And make a String object from those code points.
String s =
Arrays
.stream( firstFewCodePoints )
.collect( StringBuilder::new , StringBuilder::appendCodePoint , StringBuilder::append )
.toString();
🥦_S
Or we can use a constructor of String to take a subset of the array.
String result = new String( codePoints , 0 , 3 ) ;
🥦_S
See this code run live at IdeOne.com.
The answer by Basil nicely shows that you should work with code points instead of chars.
A String does not store Unicode code points internally, so there is no way to know which characters belong together forming a Unicode code point, without inspecting the actual contents of the string.
Unicode-aware substring
Here is a Unicode-aware substring method. Since codePoints() returns an IntStream, we can utilize the skip and limit methods to extract a portion of the string.
public static String unicodeSubstring(String string, int beginIndex, int endIndex) {
int length = endIndex - beginIndex;
int[] codePoints = string.codePoints()
.skip(beginIndex)
.limit(length)
.toArray();
return new String(codePoints, 0, codePoints.length);
}
This is what happens in the abovementioned snippet of code. We stream over the Unicode code points, skipping the first beginIndex bytes and limiting the stream to endIndex − beginIndex, and then convertb to int[]. The result is that the int array contains all Unicode code points from beginIndex up to endIndex.
At last, the String class contains a nice constructor to construct a String from an int[] with code points, so we use it to get the String.
Of course, you could tweak the method to be a little more strict by rejecting out-of-bounds values:
if (endIndex < beginIndex) {
throw new IllegalArgumentException("endIndex < beginIndex");
}
int length = endIndex - beginIndex;
int[] codePoints = string.codePoints()
.skip(beginIndex)
.limit(length)
.toArray();
if (codePoints.length < length) {
throw new IllegalArgumentException(
"begin %s, end %s, length %s".formatted(beginIndex, endIndex, codePoints.length)
);
}
return new String(codePoints, 0, codePoints.length);
Online demo
I would like to provide another point of view, on how to implement substring which is able to guarantee the returned string contains valid unicode.
Unlike answer provided by #MC Emperor, my code treats
🥦 length as 2 (Instead of 1 by #MC Emperor)
This is important, to ensure the new function's behavior will resemble as close as old String.substring.
public static int length(String string) {
if (string == null) {
return 0;
}
return string.length();
}
public static String limitLength(String string, int maxLength) {
int stringLength = length(string);
if (stringLength <= maxLength) {
return string;
}
List<Integer> codePointList = new ArrayList<>();
for (int offset = 0; offset < maxLength; ) {
final int codePoint = string.codePointAt(offset);
final int charCount = Character.charCount(codePoint);
if ((offset + charCount) > maxLength) {
break;
}
codePointList.add(codePoint);
offset += charCount;
}
int[] codePoints = new int[codePointList.size()];
for (int i = 0; i < codePoints.length; i++)
{
codePoints[i] = codePointList.get(i);
}
String result = new String(codePoints, 0, Math.min(maxLength, codePoints.length));
return result;
}
The code performance might not be efficient, if the maxLength value is large. But, I can't think of a much better way now. If you know a better way, feel free to amend the answer.
It is by design. Java provides many ways to extract individual Unicode code points from a string if it's necessary: see the Oracle tutorial.
However, most of the time it's not needed since you get the string index from a method like String.indexOf(String s) or Matcher.start(). In this case the resulting index won't point in the middle of a code point (as long as the argument s is a valid Unicode string).
It's even more common to work with regular expressions where string indexes don't come up altogether.
I am having some trouble with modifying Strings to be space delimited under the special case of adding spaces to all non-numerical characters.
My code must take a string representing a math equation, and split it up into it's individual parts. It does so using space delimits between values This part works great if the string is already delimited.
The problem is that I do not always get a space delimited input. To deal with this, I want to first insert these spaces so that the array is created properly.
What my code must do is take any character that is NOT a number, and add a space before and after it.
Something like this:
3*24+321 becomes 3 * 24 + 321
or
((3.0)*(2.5)) becomes ( ( 3.0 ) * ( 2.5 ) )
Obviously I need to avoid inserting space in the numbers, or 2.5 becomes 2 . 5, and then gets entered into the array as 3 elements. which it is not.
So far, I have tried using
String InputLineDelmit = InputLine.replaceAll("\B", " ");
which successfully changes a string of all letters "abcd" to "a b c d"
But it makes mistakes when it runs into numbers. Using this method, I have gotten that:
(((1)*(2))) becomes ( ( (1) * (2) ) ) ---- * The numbers must be separate from parens
12.7+3.1 becomes 1 2.7+3.1 ----- * 12.7 is split
51/3 becomes 5 1/3 ----- * same issue
and 5*4-2 does not change at all.
So, I know that \D can be used as a regular expression for all non-numbers in java. However, my attempts to implement this (by replacing, or combining it with \B above) have led either to compiler errors or it REPLACING the char with a space, not adding one.
EDIT:
==== Answered! ====
It wont let me add my own answer because I'm new, but an edit to neo108's code below (which, itself, does not work) did the job. What i did was change it to check isDigit, not isLetter, and then do nothing in that case (or in the special case of a decimal, for doubles). Else, the character is changed to have spaces on either side.
public static void main(String[] args){
String formula = "12+((13.0)*(2.5)-17*2)+(100/3)-7";
StringBuilder builder = new StringBuilder();
for (int i = 0; i < formula.length(); i++){
char c = formula.charAt(i);
char cdot = '.';
if(Character.isDigit(c) || c == cdot) {
builder.append(c);
}
else {
builder.append(" "+c+" ");
}
}
System.out.println("OUTPUT:" + builder);
}
OUTPUT: 12 + ( ( 13.0 ) * ( 2.5 ) - 17 * 2 ) + ( 100 / 3 ) - 7
However, any ideas on how to do this more succinctly, and also a decent explanation of StringBuilders, would be appreciated. Namely what is with this limit of 16 chars that I read about on javadocs, as the example above shows that you CAN have more output.
Something like this should work...
String formula = "Ab((3.0)*(2.5))";
StringBuilder builder = new StringBuilder();
for (int i = 0; i < formula.length(); i++){
char c = formula.charAt(i);
if(Character.isLetter(c)) {
builder.append(" "+c+" ");
} else {
builder.append(c);
}
}
Define the operations in your math equation + - * / () etc
Convert your equation string to char[]
Traverse through the char[] one char at a time and append the read char to a StringBuilder object.
If you encounter any character matching with the operations defined, then add a space before and after that character and then append this t o the StringBuilder object.
Well this is one of the algorithm you can implement. There might be other ways of doing it as well.
How do you check how many letters are in a Java string?
How do you check what letter is in a certain position in the string (i.e, the second letter of the string)?
A)
String str = "a string";
int length = str.length( ); // length == 8
http://download.oracle.com/javase/7/docs/api/java/lang/String.html#length%28%29
edit
If you want to count the number of a specific type of characters in a String, then a simple method is to iterate through the String checking each index against your test case.
int charCount = 0;
char temp;
for( int i = 0; i < str.length( ); i++ )
{
temp = str.charAt( i );
if( temp.TestCase )
charCount++;
}
where TestCase can be isLetter( ), isDigit( ), etc.
Or if you just want to count everything but spaces, then do a check in the if like temp != ' '
B)
String str = "a string";
char atPos0 = str.charAt( 0 ); // atPos0 == 'a'
http://download.oracle.com/javase/7/docs/api/java/lang/String.html#charAt%28int%29
If you are counting letters, the above solution will fail for some unicode symbols. For example for these 5 characters sample.length() will return 6 instead of 5:
String sample = "\u760c\u0444\u03b3\u03b5\ud800\udf45"; // 瘌фγε𐍅
The codePointCount function was introduced in Java 1.5 and I understand gives better results for glyphs etc
sample.codePointCount(0, sample.length()) // returns 5
http://globalizer.wordpress.com/2007/01/16/utf-8-and-string-length-limitations/
To answer your questions in a easy way:
a) String.length();
b) String.charAt(/* String index */);
1) To answer your question:
String s="Java";
System.out.println(s.length());
I could not get any of these answers to work for me using UTF-8. If you are using UTF-8, have a look at this post. I ended up using Guava's Utf8.
How can I get the int value from a string such as 423e - i.e. a string that contains a number but also maybe a letter?
Integer.parseInt() fails since the string must be entirely a number.
Replace all non-digit with blank: the remaining string contains only digits.
Integer.parseInt(s.replaceAll("[\\D]", ""))
This will also remove non-digits inbetween digits, so "x1x1x" becomes 11.
If you need to confirm that the string consists of a sequence of digits (at least one) possibly followed a letter, then use this:
s.matches("[\\d]+[A-Za-z]?")
The NumberFormat class will only parse the string until it reaches a non-parseable character:
((Number)NumberFormat.getInstance().parse("123e")).intValue()
will hence return 123.
Unless you're talking about base 16 numbers (for which there's a method to parse as Hex), you need to explicitly separate out the part that you are interested in, and then convert it. After all, what would be the semantics of something like 23e44e11d in base 10?
Regular expressions could do the trick if you know for sure that you only have one number. Java has a built in regular expression parser.
If, on the other hands, your goal is to concatenate all the digits and dump the alphas, then that is fairly straightforward to do by iterating character by character to build a string with StringBuilder, and then parsing that one.
You can also use Scanner :
Scanner s = new Scanner(MyString);
s.nextInt();
Just go through the string, building up an int as usual, but ignore non-number characters:
int res = 0;
for (int i=0; i < str.length(); i++) {
char c = s.charAt(i);
if (c < '0' || c > '9') continue;
res = res * 10 + (c - '0');
}
Perhaps get the size of the string and loop through each character and call isDigit() on each character. If it is a digit, then add it to a string that only collects the numbers before calling Integer.parseInt().
Something like:
String something = "423e";
int length = something.length();
String result = "";
for (int i = 0; i < length; i++) {
Character character = something.charAt(i);
if (Character.isDigit(character)) {
result += character;
}
}
System.out.println("result is: " + result);