I suspect not much. You might save a tiny bit in not having to set up extra hidden function calls, but who really knows. I suspect the optimizer probably does a pretty good job and likely makes them near-equal in performance.
so much better to have every developer just rewrite the algorithm from scratch every time it’s used, right?
In projects with multiple programmers you can have project level utilities library. Some projects I dealt with got such a library from me (as a partial clone of my personal one) because having a good utility library just wasn’t the previous developers’ hip old way to roll.
I usually go with something like:
for (unsigned int i = 0; i < (strings.size() - 1); i++)
{
cout << strings* << ", ";
}
cout << strings*;
Saves you a comparison/branch inside the loop. Which would be super important if you have to print out a shopping list like a billion times per second on an embedded processor or something. Actually probably not even then because the compiler would likely sort it out. Whatever.
I agree with what someone said about not aiming for code compactness though - tends to make things a bit less readable in my experience. It took me a few seconds to read and understand the code in the OP to make sure I wasn’t posting the same thing (I don’t read PHP, but still).
For some reason, I tend to do things like that this way:
String result = "";
String pfx = "";
for (i=0; i < list.size(); ++i) {
result += pfx + list.get(i);
pfx = ",";
}
;
Thereby losing a condition but gaining an assignment. I have no idea where I picked up the habit.
I considered that way and it feels more fluid than having the “if” in there - I like it more for that reason - but it’s also less obvious and that is pretty much my goal these days - make it so obvious that when I read code I don’t have to actually use much brain power.
Two things I don’t like about the substring:
- Something is getting added and then taken away - that doesn’t feel right (even though I’ve done tons of things like that, just talking theory)
- Substring and different languages: is string indexing zero based? is the 2nd parm the length of the substring or the end position, or the end position of the substring + 1? I’m constantly flipping between languages and this one requires thought due to lack of consistency.
Rant/Question:
What exactly did the designers of Java think was being gained by making the end index of the substring be a number that in no way actually represents the end index of the substring? So we have less math to do when calculating the length of the substring? WTF?
Oh, I absolutely HATE the end index of the substring method, not even going to try to debate that. I’d guess there may be some common problem that makes use of it (Since that means substring(0,0) is the empty string, which you can’t get with inclusive unless you define weird stuff like substring(0,-1)), but for general use that last index would make much more sense inclusive to me.
More to the point, when they took pains to make other aspects of the language consistent with C/C++ where practical in order to allow an easy transition for those programmers, why did they make the String object substring method work different from the C++ string::substr by taking a start and \0 terminator index instead of an index and a length?
I was trying to help you understand friedo’s comment, I didn’t make the comment.
It’s also possible friedo was implying that a good object oriented design would not require a special library of routines - but the world is a complex place and I certainly find a need for them.
But for the code in the OP it all depends on how frequently that code is being written - it takes 4 seconds to write so it would have to be encountered pretty frequently to rise to the level of requiring a utility routine. In addition, in my experience things like that are typically intertwined with more complex requirements that then become a problem when trying to use a standard routine - so it all depends.
A standardized set of routines for a project makes sense - a personal library only makes sense for personal projects.
jragon: I’ve thought about that - sacrifice elegance for 99% of the cases so we can have an elegant solution for the 1%
yabob: I wish all substring was the same, start, length - 0 based versus 1 based is a little harder because it permeates each environment - probably can’t standardize that one
No. Your language, whatever it is, has in its standard frameworks or libraries a properly implemented function for joining a list of items into a delimited string. That function properly handles edge cases, such as empty lists, multiple-character delimiters, encoding issues, and other things too numerous to mention. It is, without question, superior to anything you can come up with. It is well-tested, bug-fixed, and its behavior is well-known and well-defined.
Reinventing the wheel for trivial operations is almost never a good idea. Take the five minutes and use your googler to find the appropriate built-in function for accomplishing trivial tasks. Don’t roll your own. Doing so introduces an unnecessary dependency upon code that is untested and has not been used against all the conditions that you never thought of.
Here’s an alternate idiom that avoids the need for your initial foreach loop:
echo join( ' °F, ', $low5 ) . ' °F';
It’s faster but that probably is of no significance for most purposes.
I’d avoid using a reference in foreach simply because of the likelihood someone will come along later and misunderstand it or screw it up.
Thanks. Neat solution
I understand the points people make about it being a low priority to be this code-efficient. The thing is - I’m a little anal and making my code as minimalistic as possible (without it becoming too obfuscated) gives a kind of buzz. This is a training exercise. I probably wouldn’t be this bothered about being ‘clever’ with code on a real project… at least not in the construction phase. Maybe in the optimization phase (if there is one)
In the coding example above you definitely want to use StringBuilder() instead of String. The JVM will probably not convert your code to use StringBuilder because you’re using your own loop. E.g, the JVM will convert this: returnValue = a + “,” + b + “,” + c;.
One other subtle point about your solution which keeps it from using StringBuilder: this line does not do what you expect:
returnVal += item + ",";
The JVM guarantees the order of operations and “+=” has lower precedence than item + “,”, so what’s really happing is:
String temp = item + ",";
returnValue = returnValue + temp;
So your code is definitely creating a temporary String when logically it doesn’t need it. You can fix it by changing it to:
returnValue = returnValue + item + ",";
(Which the JVM might change to using a StringBuilder for this assignment.)
Point taken, but as the above example shows we don’t always know the intricacies of even simple routines. Besides, the Apache Commons libraries have a lot of good routines and the hour one takes to learn them all (or at least glance through them) ends up being worth the effort.
Concise coding is not about being impressive, it is about being expressive.
Consider this… you’re hacking through some horrible code. Since the author clearly is undeserving of trust, you must inspect Every. Single. Line. That being the case, when you hit a patch of code that joins a list, which scenario would you rather experience:
1: for i > 0, blah blah blah… dear God, here’s another for loop, what the hell is he doing here, what could have gone wrong here?
2: foo = String.join(’,’). Oh goody. Obviously this is a join, and I can trust it because I know commons.lang wasn’t developed by dyslexic psychopaths.
Using the most common idioms means we spend less time thinking about code and more time thinking about features, which is ultimately what we’re held accountable for.
Your point is correct. By elegant solution I was referring to an optimized loop of some sort. Of course there is an even better solution for being expressive with whatever method is used. It’s called a comment.
//make comma separated list out of items
I just strip the last seperator off too. I guess you could add a test to see if it was the last element before adding the comma, but that would seem to take an extra process or if statement for each element.
What’s more, one can probably trust that StringUtils.join() is about as efficient as it possibly can be for the general case. Concise and efficient–what’s not to love?
If anyone cares here’s how Apache Commons does the join in Java:
public static String join(Object[] array, char separator, int startIndex, int endIndex) {
if (array == null) {
return null;
}
int bufSize = (endIndex - startIndex);
if (bufSize <= 0) {
return EMPTY;
}
bufSize *= ((array[startIndex] == null ? 16 : array[startIndex].toString().length()) + 1);
StringBuffer buf = new StringBuffer(bufSize);
for (int i = startIndex; i < endIndex; i++) {
if (i > startIndex) {
buf.append(separator);
}
if (array* != null) {
buf.append(array*);
}
}
return buf.toString();
}
intercalate ", "
Example usage:
intercalate ", " $ words "Hello programmers of the SDMB"
Output:
"Hello, programmers, of, the, SDMB"
Is this, by any chance, Haskell?