IndexOf method returns 0 when it should had return -1 in C# / Java
Asked Answered
D

8

7

A friend of mine came to me with this strange behavior which i can't explain, any insight view would be appreciated.

Im running VS 2005 (C# 2.0), the following code show the behavior

int rr = "test".IndexOf("");
Console.WriteLine(rr.ToString());

the above code, print "0" which clearly show it should have return -1

This also happen in Java where the following Class show the behavior:

public class Test{
 public static void main(String[] args){
   System.out.println("Result->"+("test".indexOf("")));
 }
}

Im running Java 1.6.0_17

Dextrous answered 2/4, 2010 at 19:12 Comment(1)
Duplicate of #3873436 and #146009Charpentier
H
10

This is not an exception to the rule, but rather a natural consequence of how indexOf and startsWith are defined.

You’re claiming that "test".indexOf("") should return -1. This is essentially equivalent to the claim that "test".startsWith("") should return false. Why is this? Although this case is specifically addressed in the documentation as returning true, this is not just an arbitrary decision.

How would you decide "test".startsWith("te"), for example? The simplest way is to use recursion. Since both strings start with the character 't', you call "est".startsWith("e") and return the result. Similarly, you will call "st".startsWith("") and return the result. But you already know that the answer should be true, so that is why every string starts with "".

Hortenciahortensa answered 2/4, 2010 at 20:3 Comment(0)
A
21

Quote from the C# documentation:

If value is Empty, the return value is 0.

The behavior that you describe is entirely as expected (at least in C#).

Apace answered 2/4, 2010 at 19:14 Comment(2)
Thanks for pointing it out for C# (So it seems an Exception to the rule). On its counter part (JavaDoc), is not well explained that this behavior will be expected.Dextrous
@jcgarciam: good point; I'll update the answer indicating that it is related to C#.Sikko
G
11

0 is correct. Start at position zero and you can (trivially) match a zero-length string. Likewise, "" contains "".

Gelatin answered 2/4, 2010 at 19:13 Comment(2)
that would be fine if that would have been my example, i tried: "Test".IndexOf(""); which is different at what you explain.Dextrous
@Dextrous not really. Look at it this way; in what way does it not start with (or contain) "". Show me the character that isn't a match. There isn't one, therefore it is is a match.Gelatin
H
10

This is not an exception to the rule, but rather a natural consequence of how indexOf and startsWith are defined.

You’re claiming that "test".indexOf("") should return -1. This is essentially equivalent to the claim that "test".startsWith("") should return false. Why is this? Although this case is specifically addressed in the documentation as returning true, this is not just an arbitrary decision.

How would you decide "test".startsWith("te"), for example? The simplest way is to use recursion. Since both strings start with the character 't', you call "est".startsWith("e") and return the result. Similarly, you will call "st".startsWith("") and return the result. But you already know that the answer should be true, so that is why every string starts with "".

Hortenciahortensa answered 2/4, 2010 at 20:3 Comment(0)
G
6

0 is correct. The Javadocs point out that indexOf works as follows:

The integer returned is the smallest value k such that:

 this.startsWith(str, k)

Any string starting with "" is equal to the original string (and every string starts with ""), so the smallest k for str = "" is always 0.

Giavani answered 2/4, 2010 at 19:15 Comment(2)
Sorry, but i can't understand your reasoning on this.Dextrous
Every single string starts with "" Likewise, every single set is a superset of an empty set. Etc... It is a very convenient convention.Deirdre
M
3

Think of it this way: IndexOf, when looking for a string, will start at position 0, try to match the string, if it doesn't fit, move on to position 1, 2, etc. When you call it with an empty string, it attempts to match the empty string with the string starting at position 0 with length 0. And hooray, nothing equals nothing.

Side note: There's no real reason to use ToString when you're using Console.Write/WriteLine. The function automatically calls the ToString method of the object in question. (Unless overloading ToString)

Macedo answered 2/4, 2010 at 19:18 Comment(2)
At index position 0, "test" does not hold "nothing" it has a "t". Voted +1 for the way you put it.:)Moorehead
as ring said, at position 0 it doesn't hold "nothing". But thanks anyway! It seems this is explained in the Documentation. I will put this as an Exception to the rule of how IndexOf is suppose to works.Dextrous
D
2

It should return 0. You are looking for the first occurrence of an empty string, right? :)

Deirdre answered 2/4, 2010 at 19:15 Comment(0)
U
1

Just for the fun of it. It also works like that in python

>>> "test".startswith("")
True
>>> "test".index("")
0

Python throws a ValueError instead of the -1 that is nice.

>>> "test".index('r')
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ValueError: substring not found
Urga answered 3/4, 2010 at 1:38 Comment(0)
U
1

More fun php actually does a way better job!

php -r "print strpos('test','');"
PHP Warning:  strpos(): Empty delimiter. in Command line code on line 1
Urga answered 3/4, 2010 at 5:55 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.