Go Premium for a chance to win a PS4. Enter to Win

x
Solved

# string at particular index

Posted on 2014-11-09
Medium Priority
209 Views
Hi

I was trying below example

http://codingbat.com/prob/p121596

I was not sure how to proceed on this. I wrote some dummy code as below

How to fix and improve the my code

``````public String altPairs(String str) {
for(int i=0;i<str.length();i++)
String str2=(str.substring(i,i+1)+str.substring(i+4,i+5));
return str2;
}
``````
0
Question by:gudii9
• 34
• 24
• 5
• +1

LVL 28

Assisted Solution

dpearson earned 600 total points
ID: 40432042
You need to go through the string in jumps of 4.

So the loop will be something like "i += 4" for the step.

Then you want to get 2 letters for each step through the loop.
That's basically:
String str2=(str.substring(i,i+2));

But there's a problem.  What happens if you are looking 2 characters ahead and there's not 2 characters left in the string?

That's where I've left the problem.  So the code below doesn't exactly work:

``````public String altPairs(String str) {
int len = str.length() ;
StringBuilder result = new StringBuilder() ;

for (int i = 0 ; i < len ; i += 4) {
int end = Math.min(i+2, len) ;
String str2=(str.substring(i,i+2));
result.append(str2) ;
}

return result.toString() ;
}
``````

But you can make it work with a very small change.  Can you see where to make the fix?

Doug
0

LVL 25

Assisted Solution

chaau earned 600 total points
ID: 40432045
You have defined the str2 variable inside the for() scope. It needs to be defined outside of the scope:
``````public String altPairs(String str) {
String str2="";
for(int i=0;i<str.length();i++)
str2=(str.substring(i,i+1)+str.substring(i+4,i+5));
return str2;
}
``````
However, you also need to check for the string length to make sure substring(i+4,i+5) does not go past the last character of the string.
I propose this function:
``````String str2="";
for(int i=0;i<str.length();i+=4)
{
str2+=str.substring(i,i+2<=str.length()?i+2:i+1);
}
return str2;
``````
0

LVL 7

Author Comment

ID: 40433135
``````You have defined the str2 variable inside the for() scope. It needs to be defined outside of the scope:
``````
i got it.
``````str2+=str.substring(i,i+2<=str.length()?i+2:i+1);
``````
what is the meaning of above code

You need to go through the string in jumps of 4.

So the loop will be something like "i += 4" for the step.

0

LVL 85

Expert Comment

ID: 40433998
the loop starts with i=0
after executing i += 4, i will be 4
after executing i += 4 again,  i will be 8
0

LVL 7

Author Comment

ID: 40437881

Given a string, return a string made of the chars at indexes 0,1, 4,5, 8,9 ... so "kittens" yields "kien".

altPairs("kitten") â†’ "kien"
altPairs("Chocolate") â†’ "Chole"
altPairs("CodingHorror") â†’ "Congrr"

But the challenge statement as above did not mention about jumps of 4 right. can you please advise

``````String str2="";
for(int i=0;i<str.length();i+=4)
{
str2+=str.substring(i,i+2<=str.length()?i+2:i+1);
}
return str2;
``````

in the above working code i see jumps of 4 but not sure what is happening in below line
str2+=str.substring(i,i+2<=str.length()?i+2:i+1);
which i can translate as below more understandable to me
str2= str2+str.substring(i,i+2<=str.length()?i+2:i+1);

not clear what is being passed to substring method above as below

i,i+2<=str.length()?i+2:i+1
0

LVL 85

Expert Comment

ID: 40439007
Would it have been easier to understand if it had been
i,Math.min(str.length(),i+2)
?
0

LVL 25

Expert Comment

ID: 40439010
The operator ?: is called a ternary operator. It is a shortcut to write something in one line. Without this operator you would write:
``````// str2+=str.substring(i,i+2<=str.length()?i+2:i+1); is equivalent to
if(i+2<=str.length())
str2+=str.substring(i,i+2);
else
str2+=str.substring(i,i+1);
``````
0

LVL 7

Author Comment

ID: 40440595
str2+=str.substring(i,i+1);
i do not see i,i+1 in below statement
str2+=str.substring(i,i+2<=str.length()?i+2:i+1); is equivalent to
0

LVL 28

Expert Comment

ID: 40440685
I think the use of a tenary operator is just confusing things here.

Since this question seems to be getting more tangled rather than less, I'm going to repost the code I posted at the very top of this question and make the one small edit:

String str2=str.substring(i,i+2);
=>
String str2=str.substring(i,end);

that was required to have it solve the problem.

It relies on knowing that Math.min here:
int end = Math.min(i+2, len) ;

puts the smaller of "i+2" and "len" into the variable end.

Is this clearer?

``````public String altPairs(String str) {
int len = str.length() ;
StringBuilder result = new StringBuilder() ;

for (int i = 0 ; i < len ; i += 4) {
int end = Math.min(i+2, len) ;
String str2=str.substring(i,end);
result.append(str2) ;
}

return result.toString() ;
}
``````
0

LVL 7

Author Comment

ID: 40444062
0,1, 4,5, 8,9

Given a string, return a string made of the chars at indexes 0,1, 4,5, 8,9 ... so "kittens" yields "kien".

altPairs("kitten") â†’ "kien"
altPairs("Chocolate") â†’ "Chole"
altPairs("CodingHorror") â†’ "Congrr"

in the chalenge above numbers given right. Is it is like fibonacci series?
i do not see any pattern. what comes after 9?

I wonder why we are incrementing by 4
0

LVL 85

Expert Comment

ID: 40444184
It is true that there are an infinite number of different series that start 0,1, 4,5, 8,9 ...,
so the problem is technically underspecified, most people seem to be interpreting it as
0,1,
4,5,
8,9,
8+4,8+4+1,
12+4,12+4+1,
16+4,16+4+1,
20+4,20+4+1,
24+4,24+4+1,
...
(and there are still an infinite number of different ways to extend that pattern, but none of the test strings are that long, so it doesn't really matter)
0

LVL 28

Expert Comment

ID: 40445980
I wonder why we are incrementing by 4

We're incrementing by 4 because that's what the pattern suggested we needed to do.  It's not the fibonacci series.  The sequence is just the pair (0,1) and then adding 4 to generate the next pair (4,5) and 4 to get the next pair (8,9) etc.

So overall we get (0,1,4,5,8,9,...)
0

LVL 7

Author Comment

ID: 40447259
The sequence is just the pair (0,1) and then adding 4 to generate the next pair (4,5) and 4 to get the next pair (8,9) etc.

now i understand the pattern

for (int i = 0 ; i < len ; i += 4) {
int end = Math.min(i+2, len) ;
String str2=str.substring(i,end);

what are we doing in above 4 lines after incrementing by 4 to get the next set of 2 numbers? why we are getting substring i till end(excluding end ofcourse) all the way?
0

LVL 85

Expert Comment

ID: 40448973
when i==0, we want str.substring(0,2), unless Math.min(i+2, len)  < 2, in which case we want  str.substring(0,len),
0

LVL 7

Author Comment

ID: 40449946
unless Math.min(i+2, len)  < 2
this never happens right even if you take i as 0
0

LVL 85

Expert Comment

ID: 40449987
len < i+2 can happen
0

LVL 7

Author Comment

ID: 40450103
how and when
2<=2 can happen but not 2<2 right?
0

LVL 85

Expert Comment

ID: 40450115
2<=2 is always true
2<2  is never true
0

LVL 7

Author Comment

ID: 40450149
correct.

``````public String altPairs(String str) {
int len = str.length() ;
StringBuilder result = new StringBuilder() ;

for (int i = 0 ; i < len ; i += 4) {
// int end = Math.min(i+2, len) ;
int end=len;
String str2=str.substring(i,end);
result.append(str2) ;
}

return result.toString() ;
}
``````
when i commented above Math.min function line i am failing in all test cases where length is more than 2
``````Expected	Run
altPairs("kitten") â†’ "kien"	"kittenen"	X
altPairs("Chocolate") â†’ "Chole"	"Chocolateolatee"	X
altPairs("CodingHorror") â†’ "Congrr"	"CodingHorrorngHorrorrror"	X
altPairs("yak") â†’ "ya"	"yak"	X
altPairs("ya") â†’ "ya"	"ya"	OK
altPairs("y") â†’ "y"	"y"	OK
altPairs("") â†’ ""	""	OK
altPairs("ThisThatTheOther") â†’ "ThThThth"	"ThisThatTheOtherThatTheOtherTheOtherther"	X
``````

i did not completely get this Math.min function use here.
0

LVL 85

Expert Comment

ID: 40450158
0

LVL 7

Author Comment

ID: 40450217
0 length string("") take 2 as end..so appends 0,1 index characters which are"" and ""
1 length string("y") take 2 as end..so appends 0,1 index characters which are"y" and ""
2 length string("ya" take 2 as end..so appends 0,1 index characters which are"y" and "a"
3 length string("yak") take 2 as end..so appends 0,1 index characters which are"y" and "a" in first iteration(when i=0) and appends k in second iteration(when i=1)
6 length string("kitten") 2 as end....so appends 0,1 index characters which are"k" and "i" in first iteration(when i=0) and appends t,t in second iteration(when i=1) and  appends e,n in second iteration(when i=2)

but we are moving i by 4 after each iteration right?? please advise
0

LVL 85

Accepted Solution

ozo earned 800 total points
ID: 40450286
3 length string("yak") take 2 as end..so appends 0,1 index characters which are"y" and "a" in first iteration(when i=0) and appends k in second iteration(when i=1)
No.  After i += 4,
i < len becomes false, so the second iteration is not executed
6 length string("kitten") 2 as end....so appends 0,1 index characters which are"k" and "i" in first iteration(when i=0) and appends t,t in second iteration(when i=1) and  appends e,n in second iteration(when i=2)
No.  in second iteration(when i=4) "e" and "n" are appended
0

LVL 7

Author Comment

ID: 40450446
it all make better sense now.
``````public String altPairs(String str) {
int len = str.length() ;
StringBuilder result = new StringBuilder() ;

for (int i = 0 ; i < len-1 ; i += 4) {
int end = Math.min(i+2, len) ;
//int end=len;
String str2=str.substring(i,end);
result.append(str2) ;
}

return result.toString() ;
}
``````

when i wrote as above by doing -1 i got couple of tests failied
``````Expected	Run
altPairs("kitten") â†’ "kien"	"kien"	OK
altPairs("Chocolate") â†’ "Chole"	"Chol"	X
altPairs("CodingHorror") â†’ "Congrr"	"Congrr"	OK
altPairs("yak") â†’ "ya"	"ya"	OK
altPairs("ya") â†’ "ya"	"ya"	OK
altPairs("y") â†’ "y"	""	X
altPairs("") â†’ ""	""	OK
altPairs("ThisThatTheOther") â†’ "ThThThth"	"ThThThth"	OK
``````
i wonder why they failed esp.
altPairs("Chocolate") â†’ "Chole"      "Chol"      X
0

LVL 28

Expert Comment

ID: 40450534
for (int i = 0 ; i < len-1 ; i += 4)

Is causing the loop to stop too soon (the -1 makes it stop 1 before the last character).

You can either have:
for (int i = 0 ; i < len ; i += 4)
or
for (int i = 0 ; i <= len-1 ; i += 4)

Both are equivalent.  So if you prefer to think about "len-1" you need to use "<=".

The reason most people write:
for (int i = 0 ; i < len ; i += 4)
is because the loop starts from 0, not 1.

So
for (int i = 0 ; i < 10 ; i++)
means to loop 10 times (0,1,2,3,4,5,6,7,8,9).  So it's easier to read when the "10" is the limit or "len" is the limit in this loop.

For that to work, we use i < 10 or i < len.

Does that make sense?

Doug
0

LVL 7

Author Comment

ID: 40450563
yes.

I wonder why it failed for below test case while using i < len-1
altPairs("Chocolate") â†’ "Chole"      "Chol"      X
0

LVL 28

Expert Comment

ID: 40450580
"Chocolate" is a string of length 9.  So len - 1 is 8.

This means the loop becomes:
for (i = 0 ; i < 8 ; i += 4)
which means we get (0,4) as the values for i instead of (0,4,8) if the test was i < len.

So we miss the last group of characters - the trailing "e" in this case.

Doug
0

LVL 7

Author Comment

ID: 40453614
``````altPairs("y") â†’ "y"	""	X
``````

0

LVL 7

Author Comment

ID: 40453620
``````int end = Math.min(i+2, len) ;
``````

so basically we are getting end to feed to substring method to get next set of characters to be appeneded to string builder right?
0

LVL 85

Expert Comment

ID: 40453642
"y" is a string of length 1, so len - 1 is 0, so altPairs("y") failed for the same reason as altPairs("Chocolate")

we are getting end to feed to substring method
correct
0

LVL 85

Expert Comment

ID: 40454432
It can actually be useful to loop only for  i<len-1, because that guarantees that within the loop, str.substring(i,i+2) will not be out of bounds, which makes it unnecessary to repeatedly guard for that condition inside the loop body.
After the loop is done, we can then do a single check to see if we need to append one more character in the case where we stopped to soon to get the final length 1 piece of str.substring(i,len):

public String altPairs(String str) {
int len = str.length() ;
StringBuilder result = new StringBuilder() ;
int i;
for ( i = 0 ; i < len-1 ; i += 4) {
result.append(str.substring(i,i+2)) ;
}
if( i==len-1 ){
result.append(str.substring(i)) ;
}
return result.toString() ;
}
0

LVL 7

Author Comment

ID: 40455201
I see above solution more clear.
altPairs("") â†’ ""      ""      OK
will not go to if loop of above solution right.

only when len is one like "y" string it goes to aboe if loop for rest of scenarios just go to for loop and appends the string using substring method and returns as result.toString right?
0

LVL 7

Author Comment

ID: 40455217
``````altPairs("") â†’ ""	""	OK
``````

how it works for above case
i<len-1(here len-1 becomes -1 for i=0 right)
0

LVL 85

Expert Comment

ID: 40455231
for ( i = 0 ; i < len-1 ; i += 4) does not go into the loop body when len==0 or len==1
for ( i = 0 ; i < len ; i += 4) does not go into the loop body when len==0 but does go into the loop body when len==1
0

LVL 7

Author Comment

ID: 40455376
correct
public String altPairs(String str) {
int len = str.length() ;
StringBuilder result = new StringBuilder() ;
int i;
for ( i = 0 ; i < len-1 ; i += 4) {
result.append(str.substring(i,i+2)) ;
}
if( i==len-1 ){
result.append(str.substring(i)) ;
}
return result.toString() ;
}

for ( i = 0 ; i < len-1 ; i += 4) does not go into the loop body when len==0 or len==1

How above solution is working then for len==0 and len==2. please advise
0

LVL 7

Author Comment

ID: 40455484
when len==1 i can visualize it going into if loop and eppending as below
if( i==len-1 ){
result.append(str.substring(i)) ;
}

but if len==0 how solution passed the test case(for string like""). please advise
0

LVL 85

Expert Comment

ID: 40456362
if len==0, the solution of http#a40454432 reduces to

public String altPairs(String str) {
int len = str.length() ;
StringBuilder result = new StringBuilder() ;
int i;
// don't execute code in for loop body, don't execute code in if body
return result.toString() ;
}
0

LVL 7

Author Comment

ID: 40457576
if len==0, the solution of http#a40454432 reduces to
i could not see above mentioned url--a40454432

http://www.experts-exchange.com/Programming/Languages/Java/Q_40454432.html

i tied this also
http://www.experts-exchange.com/Programming/Languages/Java/Q_a40454432.html
is it is spearate question or separate comment on this question?
0

LVL 7

Author Comment

ID: 40457589
ozo2014-11-19 at 23:49:00ID: 40454432

i see without a
0

LVL 7

Author Comment

ID: 40457598
if len==0, the solution of http#a40454432 reduces to

so the code supposed to be as below
``````public String altPairs(String str) {
int len = str.length() ;
StringBuilder result = new StringBuilder() ;
int i;
// don't execute code in for loop body, don't execute code in if body
return result.toString() ;
}
``````
``````public String altPairs(String str) {
int len = str.length() ;
StringBuilder result = new StringBuilder() ;
int i;
for ( i = 0 ; i < len-1 ; i += 4) {
result.append(str.substring(i,i+2)) ;
}
if( i==len-1 ){
result.append(str.substring(i)) ;
}
return result.toString() ;
}
``````
0

LVL 7

Author Comment

ID: 40457606
I see if the len==0 then it directly goes to

return result.toString() ; without going to for and if loop.

0

LVL 85

Expert Comment

ID: 40457615
if the len==0 then it directly goes to

return result.toString() ;
That's correct

http#a40454432
should have been
http:#a40454432
0

LVL 7

Author Comment

ID: 40457656
``````// str2+=str.substring(i,i+2<=str.length()?i+2:i+1); is equivalent to
if(i+2<=str.length())
str2+=str.substring(i,i+2);
else
str2+=str.substring(i,i+1)
``````

i am still trying to understand how these two are  equivalent.
substring second argument is
i+2<=str.length()?i+2:i+1
which means
if i+2<=str.length() is true take i+2 //when this case happen?
if i+2<=str.length() is false take i+1 as value.//when this case happen?
0

LVL 85

Expert Comment

ID: 40457677
when i+2<=str.length() is true,  i+2<=str.length()?i+2:i+1 is i+2
when i+2<=str.length() is false, i+2<=str.length()?i+2:i+1 is i+1

https://docs.oracle.com/javase/tutorial/java/nutsandbolts/op2.html
0

LVL 7

Author Comment

ID: 40457687
``````altPairs("kitten") â†’ "kien"	"kien"	OK
``````
for above example str.length is 6 right
for the first iteration i=0

so
``````str2+=str.substring(i,i+2<=str.length()?i+2:i+1);
``````
i+2<=str.length()?i+2:i+1 becomes 2<=6 since true takes i+2 which is 2
so it should print 0,2 indexed characters as first set right before incrementing by 4 for next set.

But we do not want 0,2 but instead we want 0,1.

Please correct where i am thinking wrong. The test cases are passing so my understanding is wrong above some where. please advise
0

LVL 85

Expert Comment

ID: 40457696
"kitten".substring(0,2) is "ki", which we want
0

LVL 85

Expert Comment

ID: 40457798
One way to visualize it could be to think of the index numbers as being between the characters in the string, and the substring character being between the selected index numbers
`````` _ _
k i t t e n
| ^ | ^ ^ ^ ^
0 1 2 3 4 5 6
``````
0

LVL 7

Author Comment

ID: 40457808
"kitten".substring(0,2) is "ki", which we want

Given a string, return a string made of the chars at indexes 0,1, 4,5, 8,9 ... so "kittens" yields "kien".

altPairs("kitten") â†’ "kien"
altPairs("Chocolate") â†’ "Chole"
altPairs("CodingHorror") â†’ "Congrr"

challenge says 0,1 then 4,5 then 8,9 right
0

LVL 7

Author Comment

ID: 40457810
Oh well i see substring end is excluded right unlike start index.
Ok i got it now
0

LVL 85

Expert Comment

ID: 40457825
challenge says at indexes 0,1
challenge does not say substring(0,1)
0

LVL 7

Author Comment

ID: 40457829
altPairs("y") â†’ "y"      "y"      OK
altPairs("") â†’ ""      ""      OK

these are only two scenarios where false returns
``````i+2<=str.length()?i+2:i+1
``````

so  i+1 is returned.
so the substring becomes

altPairs("y") â†’ "y"      "y"      OK        ===>substring(0,1)  --->so give back y
altPairs("") â†’ ""               ====>substring(0,1) so gives back ""

But to begin with how we know to compare with i+2 as below(not i or i+1)
i+2<=
0

LVL 85

Expert Comment

ID: 40457841
altPairs("") makes len==0
so whether we loop for ( i = 0 ; i < len-1 ; i += 4)
or for ( i = 0 ; i < len ; i += 4)
the loop condition starts out false, so we don't even enter the loop body

altPairs("y") makes str.length()==1
so i+2<str.length() is false, which means i+2<=str.length()?i+2:i+1 is i+1
0

LVL 7

Author Comment

ID: 40458060
``````altPairs("CodingHorror") â†’ "Congrr"	"Congrr"	OK
``````

how we got Congrr??

substring second argument is
i+2<=str.length()?i+2:i+1
which means
if i+2<=str.length() is true take i+2

so we get substring(0,2) which is "Co" in the first iteration

then i incremented by 4 so 0 becomes 4
6<=12 true so take i+2
so we get substring(4,6) which is "ng" in the second iteration

then i incremented by 4 so 4 becomes 8
8<=12 true so take i+2
so we get substring(8,10) which is "rr" in the second iteration

so i+1 scenario only comes for "y"(1 character strings)
if empty string wil not even go inside the loop.

0

LVL 85

Expert Comment

ID: 40458079
i+1 scenario also comes for "Chocolate"
0

LVL 7

Author Comment

ID: 40458201
i+1 scenario also comes for "Chocolate"
0

LVL 85

Expert Comment

ID: 40458858
When i==8
0

LVL 7

Author Comment

ID: 40463155
for(int i=0;i<str.length();i+=4)
the loop condition starts out false, so we don't even enter the loop body when i=8 right?
0

LVL 85

Expert Comment

ID: 40463431
"Chocolate".length() ==9
8<9 is true
0

LVL 7

Author Comment

ID: 40466753
``````public class Test33 {

/**
* @param args
*/
public static void main(String[] args) {
// TODO Auto-generated method stub
//altPairs("chocolate");
System.out.println("value is-->"+altPairs("chocolate"));
}

public static String altPairs(String str) {
String str2="";
for(int i=0;i<str.length();i+=4)
{
str2+=str.substring(i,i+2<=str.length()?i+2:i+1);
}
return str2;
}
}
``````
i got output
value is-->chole

how we got chole??

substring second argument is
i+2<=str.length()?i+2:i+1
which means
if i+2<=str.length() is true take i+2

so we get substring(0,2) which is "ch" in the first iteration

then i incremented by 4 so 0 becomes 4
6<=8 true so take i+2
so we get substring(4,6) which is "ol" in the second iteration

//chocolate
then i incremented by 4 so 4 becomes 8
8<=8 true so take i+2
so we get substring(8,10) which is "e?" in the third iteration

so i+1 is not coming right.

0

LVL 85

Expert Comment

ID: 40466769
8+2<="Chocolate".length() is not true
0

LVL 7

Author Comment

ID: 40466892
i got output
value is-->chole

how we got chole??

substring second argument is
i+2<=str.length()?i+2:i+1
which means
if i+2<=str.length() is true take i+2 (since2<=8)

so we get substring(0,2) which is "ch" in the first iteration

then i incremented by 4 so 0 becomes 4
6<=8 true so take i+2
so we get substring(4,6) which is "ol" in the second iteration

//chocolate
then i incremented by 4 so 4 becomes 8
10<=8 false so take i+1
so we get substring(8,9) which is "e" in the third iteration

so i+1 is  coming right.

0

LVL 85

Expert Comment

ID: 40466918
"Chocolate".length() is 9, not 8
0

LVL 7

Author Comment

ID: 40467003
i got output
value is-->chole

how we got chole??

substring second argument is
i+2<=str.length()?i+2:i+1
which means
if i+2<=str.length() is true take i+2 (since2<=9)

so we get substring(0,2) which is "ch" in the first iteration

then i incremented by 4 so 0 becomes 4
6<=9 true so take i+2
so we get substring(4,6) which is "ol" in the second iteration

//chocolate
then i incremented by 4 so 4 becomes 8
10<=9 false so take i+1
so we get substring(8,9) which is "e" in the third iteration
so i+1 is  coming right.
0

LVL 7

Author Comment

ID: 40474441
0

LVL 85

Expert Comment

ID: 40484520
yes
0

LVL 7

Author Comment

ID: 40486794
thank you
0

## Featured Post

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

When we want to run, execute or repeat a statement multiple times, a loop is necessary. This article covers the two types of loops in Python: the while loop and the for loop.
A solution for Fortify Path Manipulation.
The goal of the video will be to teach the user the difference and consequence of passing data by value vs passing data by reference in C++. An example of passing data by value as well as an example of passing data by reference will be be given. Botâ€¦
How to fix incompatible JVM issue while installing Eclipse While installing Eclipse in windows, got one error like above and unable to proceed with the installation. This video describes how to successfully install Eclipse. How to solve incompaâ€¦
###### Suggested Courses
Course of the Month11 days, 2 hours left to enroll