When no auto-list-completion is required, catoptions package's \indrisloop can handle any list separator. The \newforeach macro can naturally accept any type of list separator and it can do list completion, but it is not yet on CTAN. Here is a \indrisloop solution. This should work even when the list separator was active. As you will notice in the result of the example, spurious spaces between the elements of the list are removed.
\documentclass{article}
\usepackage{catoptions}
\begin{document}
\def\bombadil#1{%
\typeout{Doing item: #1}%
\edef\transformedlist{%
\ifdefFT\transformedlist{}{\expandcsonce\transformedlist}%
\unexpanded{\\{#1}}%
}%
}
% \indrisloop[<separator>]{<list>}{<callback>}
\indrisloop[|]{%
David Carlisle, item 1 |
Heiko Oberdiek, item 2 |
David Salomon, item 3 |
Frank Mittelbach, item 4 |
Donald Arseneau; item 5
}\bombadil
\show\transformedlist
\end{document}
{\show}
> \transformedlist=macro:
\\{David Carlisle, item 1}\\{Heiko Oberdiek, item 2}\\{David Salomon, item 3}
\\{Frank Mittelbach, item 4}\\{Donald Arseneau; item 5}.
l.21 \show\transformedlist
D.E. Knuth liked to use \\ as a list separator.
You can transform an arbitrary list into a comma-separated list using the following \makeintocommalist.
% \makeintocommalist{<original.parser>}{<orig.list.cmd>}{<transformed.list.cmd>}
\def\makeintocommalist#1#2#3{%
\def#3{}%
\def\bombadil##1{%
\edef#3{%
\expandcsonce#3{\unexpanded{##1}}%
\iflastindris\else,\fi
}%
}%
\indrisloop*[#1]{#2}\bombadil
}
Example:
\def\alist{%
David Carlisle, item 1 |
Heiko Oberdiek, item 2 |
David Salomon, item 3 |
Frank Mittelbach, item 4 |
Donald Arseneau; item 5 |
Enrico Gregorio/another great |
Ulrich Diez, yes! |
Joseph Wright, also/+
}
\makeintocommalist{|}\alist\blist
\show\blist
> \blist=macro:->
{David Carlisle, item 1},{Heiko Oberdiek, item 2},{David Salomon, item 3},
{Frank Mittelbach, item 4},{Donald Arseneau; item 5},{Enrico Gregorio/another great},
{Ulrich Diez, yes!},{Joseph Wright, also/+}.
l.53 \show\blist
EDIT
Now I remember that the catoptions package has a \cptforeach command that does exactly what you wanted. But it doesn't do auto-completion of lists. See it in action below. It is happy with arbitrary (even weird) list item separators.
% \cptforeach[<optional.sep>] <holders> \in <list> \do {<callback>}
% Note the list separators in these loops:
\tikz[shading=ball]
\cptforeach[:] \x+\cola \in 0+red : 1+green : 2+blue : 3+yellow \do {%
\cptforeach[|] \y;\colb \in {0;red | 1;green | 2;blue | 3;yellow} \do {%
\shade[ball color=\cola!50!\colb] (\x,\y) circle (0.4cm);
}%
};

The above is equivalent to
\tikz[shading=ball]
\cptforeach \x/\cola \in 0/red, 1/green, 2/blue, 3/yellow \do {%
\cptforeach \y/\colb \in {0/red, 1/green, 2/blue, 3/yellow} \do {%
\shade[ball color=\cola!50!\colb] (\x,\y) circle (0.4cm);
}%
};
e.g.) where I don't want a separation. Manually putting.|at the end of a sentence will be much easier (or!|or?|) – Tom Bombadil Sep 19 '12 at 10:53