Issue with char and string overlap

monarch_dodra monarchdodra at gmail.com
Fri Jul 19 10:37:45 PDT 2013


On Friday, 19 July 2013 at 17:18:00 UTC, JS wrote:
> I'm trying to create a split function that can handle both char 
> and string delims. I initially created two separate functions 
> but this doesn't work for default parameters since the compiler 
> doesn't know which one to choose(but in this case both would 
> work fine and it would be nice to inform the compiler of that).

Simply provide a default parameter for *one* of the functions. EG:
string[] split(string s, char d = ' ');
string[] split(string s, string d);

This lifts the ambiguity. If *both* have default params, then the
ambiguity is simply not solvable, even by a human being.

Another solution is the "no default multiple sig" option, eg:
string[] split(string s)
{
      return split(s, ' ');
}
string[] split(string s, char d);
string[] split(string s, string d);

PS: Are you doing this to learn? std.array.split does the same
thing for you.

> I then tried to template and conditionally code the two but it 
> still doesn't work:
>
> both functions work separately but when i uncomment the string 
> version I get an error about the string version shadowing.
>
> import std.stdio, std.cstream;
>
> string[] split(T)(string s, T d) if (is(T == char) || is(T == 
> string))
> {
> 	int i = 0, oldj = 0; bool ok = true;
> 	string[] r;
> 	foreach(j, c; s)
> 	{
> 		static if (is(T == char))
> 		{
> 			if (c == d)
> 			{
> 				if (!ok) { oldj++; continue; }
> 				if (r.length <= i) r.length += 5;
> 				r[i] = s[oldj..j];
> 				i++; oldj = j+1;
> 				ok = false;
> 			} else if (!ok) ok = true;
> 		}
> 		else if (is(T == string))
> 		{
> 		/*
> 			for(int j = 0; j < s.length - d.length; j++)
> 			{
> 				if (s[j..j + d.length] == d)
> 				{
> 					if (!ok) { oldj++; continue; }
> 					if (i == r.length) r.length += 5;
> 					r[i] = s[oldj..j - d.length + 1];
> 					i++; oldj = j + d.length;
> 					ok = false;
> 				} else if (!ok) ok = true;
> 		
> 			}
> 		*/
> 		}
> 	}
> 	if (oldj < s.length)
> 	{
> 		if (r.length <= i) r.length++;
> 		r[i] = s[oldj..$];
> 		i++;
> 	}
> 	r.length = i;
> 	return r;
> }
>
>
> string[] splitS(string s, string d = " ")
> {
> 	int i = 0, oldj = 0; bool ok = true;
> 	string[] r;
> 	for(int j = 0; j < s.length - d.length; j++)
> 	{
> 		if (s[j..j + d.length] == d)
> 		{
> 			if (!ok) { oldj++; continue; }
>                         if (r.length <= i) r.length += 5;
> 			r[i] = s[oldj..j - d.length + 1];
> 			i++; oldj = j + d.length;
> 			ok = false;
> 		} else if (!ok) ok = true;
> 		
> 	}
> 	if (oldj < s.length)
> 	{
> 		if (r.length <= i) r.length++;
> 		r[i] = s[oldj..$];
> 		i++;
> 	}
>
> 	r.length = i;
> 	return r;
> }
>
> void main(string[] args)
> {
>
> 	auto s = splitS("abc bas   ccc", " ");
> 	
> 	foreach(a; s) writeln(a);
> 	
> 	din.getc();
> }


More information about the Digitalmars-d-learn mailing list