Multiple returns from a class?

N

Naveen Reddy

Hello all,
I'm a Java & OOPS newbie (the question below will make that clear :)
I'm trying to return more than one value from a class.
Could anyone please give some pointers on this?

I need to assign two variables, classPathSeparator and
filePathSeparator based on the platform the program is being run on
(Solaris or WIN). The initial program works fine.

============================================================================
public class multipleReturn {

public static void main ( String args[] ) {

String filePathSeparator = getFilePathSeparator() ;
System.out.println("File Path Separator is: " +
filePathSeparator) ;

String classPathSeparator = getClassPathSeparator() ;
System.out.println("Class Path Separator is: " +
classPathSeparator) ;
}


public static String getFilePathSeparator() {
// For a variety of reasons, I really cant use the
// Sysem Property , "file.separator".
String os = System.getProperty("os.name") ;
String fileSeparator = null ;

if ( os.equals("SunOS") ) {
fileSeparator = "/" ;
} else {
fileSeparator = "\\" ;

}

return fileSeparator ;
}

public static String getClassPathSeparator() {
String os = System.getProperty("os.name") ;
String classSeparator = null ;

if ( os.equals("SunOS") ) {
classSeparator = ":" ;
} else {
classSeparator = ";" ;
}

return classSeparator ;
}
}

============================================================================

I'm trying to get it working in a more elegant way.
I realize that the code in the two classes is pretty much the same and
want to write a single class, which returns classpath and filepath
separators.

But, I dont see a way to return two strings.

a) Do I have to return an array? And then index out of this array to
get the classpath or filepath separators.

b) Can I write an object which holds these values and return that
object?
How do I then 'retrieve' any one single separator from the returned
values?

Could anyone please point me in the right direction.

Thanks for your time,
Reddy
 
C

Chris Smith

Naveen said:
Hello all,
I'm a Java & OOPS newbie (the question below will make that clear :)
I'm trying to return more than one value from a class.
Could anyone please give some pointers on this?

Your question doesn't make sense. Classes don't return values at all.
Methods return values, and a method can't return more than one.
I'm trying to get it working in a more elegant way.
I realize that the code in the two classes is pretty much the same and
want to write a single class, which returns classpath and filepath
separators.

There's only one class there (it's called 'multipleReturn', though
convention would have it called 'MultipleReturn' instead and you
probably want to consider making the change.)

Where there are two of is methods. If you want to reduce that to only
one method, you'll need to encapsulate the result:

class SystemInfo
{
private String fileSeparator;
private String classPathSeparator;

... constructor and accessors ...
}

public SystemInfo getSystemInfo()
{
if (...) return new SystemInfo("/", ":");
else if (...) return new SystemInfo ("\\", ";");
else ...
}
a) Do I have to return an array? And then index out of this array to
get the classpath or filepath separators.

No, bad idea! Arrays are not the right abstraction here. Returning an
array would imply that the two Strings mean the same thing, and there is
simply a sequence of answers to the same question. What you've got is a
multi-part answer where each part answers a different piece of the
question, and that's not what arrays are designed for.
b) Can I write an object which holds these values and return that
object?
How do I then 'retrieve' any one single separator from the returned
values?

Accessor methods in the class you write to hold the values.

--
www.designacourse.com
The Easiest Way to Train Anyone... Anywhere.

Chris Smith - Lead Software Developer/Technical Trainer
MindIQ Corporation
 
L

Larry Coon

Naveen said:
Hello all,
I'm a Java & OOPS newbie (the question below will make that clear :)
I'm trying to return more than one value from a class.
Could anyone please give some pointers on this?

Assuming you mean "method" and not "class" (classes don't return
values -- methods do), you could write a class to encapsulate your
return values. Don't use an array -- it'll work, but it's not the
abstraction that makes sense here.

Here's a general example:

public class TwoStrings {
public String s1, s2;

public TwoStrings(String s1, String s2) {
this.s1 = s1;
this.s2 = s2;
}
}

Your method's return statement looks like this:
return new TwoStrings("First string", "Second string");

Your caller does something like this:

TwoStrings result = myMethod();
String s1 = result.s1;
String s2 = result.s2;

You could also argue for the Strings in the class being
private, and using "getter" methods to access them. However,
since this class only encapsulates a two-part result set,
there isn't a lot of reason to add the extra layer of data
hiding in this particular case. (If the return value is a
single scalar value you'd just return it and access it, and
the fact that it's two values instead of one in this case
doesn't add any real reason for data hiding.)
 
D

david m-

Chris Smith said:
Your question doesn't make sense. Classes don't return values at all.
Methods return values, and a method can't return more than one.


There's only one class there (it's called 'multipleReturn', though
convention would have it called 'MultipleReturn' instead and you
probably want to consider making the change.)

Where there are two of is methods. If you want to reduce that to only
one method, you'll need to encapsulate the result:

class SystemInfo
{
private String fileSeparator;
private String classPathSeparator;

... constructor and accessors ...
}

public SystemInfo getSystemInfo()
{
if (...) return new SystemInfo("/", ":");
else if (...) return new SystemInfo ("\\", ";");
else ...
}


No, bad idea! Arrays are not the right abstraction here. Returning an
array would imply that the two Strings mean the same thing, and there is
simply a sequence of answers to the same question. What you've got is a
multi-part answer where each part answers a different piece of the
question, and that's not what arrays are designed for.


Accessor methods in the class you write to hold the values.

--
www.designacourse.com
The Easiest Way to Train Anyone... Anywhere.

Chris Smith - Lead Software Developer/Technical Trainer
MindIQ Corporation


Shouldn't you be using

java.lang.System.getProperty()

like so ...

import java.util.*;

public class SysProp
{
public static void main(String[] args)
{
Properties properties = System.getProperties();

System.out.println("file.separator = " +
properties.getProperty("file.separator") );
System.out.println("path.separator = " +
properties.getProperty("path.separator") );
}
}

david m.
 
R

Roedy Green

Your question doesn't make sense. Classes don't return values at all.
Methods return values, and a method can't return more than one.

For a method to return multiple values, you can wrap them in a
Object[] array or create a custom object with fields. You can also
split the method in two, to return one value per call.


There is no way to directly return tuples as you can in some other
languages.
 
C

Chris Smith

david said:
Shouldn't you be using

java.lang.System.getProperty()

No. I'm not familiar with the OP's situation, but since the post said
something like "for a variety of reasons, I can't use getProperty", I'd
say it's a safe bet that the OP probably shouldn't be using getProperty,
or at least isn't interested in hearing about it.

It's hard to imagine why that's the case, but two possibilities spring
to mind. Either: (a) the OP is implementing System.getProperty in a
clean-room implementation of the Java API, or (b) this is just an
example of a more general question about what to do with multiple return
values.

--
www.designacourse.com
The Easiest Way to Train Anyone... Anywhere.

Chris Smith - Lead Software Developer/Technical Trainer
MindIQ Corporation
 
A

Andrew Hobbs

Naveen Reddy said:
Hello all,
I'm a Java & OOPS newbie (the question below will make that clear :)
I'm trying to return more than one value from a class.
Could anyone please give some pointers on this?

I need to assign two variables, classPathSeparator and
filePathSeparator based on the platform the program is being run on
(Solaris or WIN). The initial program works fine.

As others have said you cannot return more than one value or object. What
is your problem though? Why do you want to complicate everything by using a
method which has to have extra code to combine two values, and then extra
code to extract the two values? Surely you already have easy access to the
two different static methods which return exactly what you want. Why not
just use them as is, albeit with a bit of rewriting.

eg
public class multipleReturn {
public static final String SUN_FILE_SEPARATOR = "/";
public static final String OTHER_FILE_SEPARATOR = "\\";
public static final String SUN_FILE_SEPARATOR = ":";
public static final String OTHER_FILE_SEPARATOR = ";";

private static String os = null;

/**
* This means that the program only has to find the os value once.
* This works if the value will not change while the program is running.
*
*/
private static boolean isSunOS() {
if(os == null)
os = System.getProperty("os.name") ;
return os.equals("SunOS");
}

public static String getFilePathSeparator() {
return isSunOS() ? SUN_FILE_SEPARATOR :
OTHER_FILE_SEPARATOR;
}
}


public static String getClassPathSeparator() {
return isSunOS() ? SUN_CLASS_SEPARATOR :
OTHER_CLASS_SEPARATOR;
}
}

============================================================================
public class multipleReturn {

public static void main ( String args[] ) {

String filePathSeparator = getFilePathSeparator() ;
System.out.println("File Path Separator is: " +
filePathSeparator) ;

String classPathSeparator = getClassPathSeparator() ;
System.out.println("Class Path Separator is: " +
classPathSeparator) ;
}


public static String getFilePathSeparator() {
// For a variety of reasons, I really cant use the
// Sysem Property , "file.separator".
String os = System.getProperty("os.name") ;
String fileSeparator = null ;

if ( os.equals("SunOS") ) {
fileSeparator = "/" ;
} else {
fileSeparator = "\\" ;

}

return fileSeparator ;
}

public static String getClassPathSeparator() {
String os = System.getProperty("os.name") ;
String classSeparator = null ;

if ( os.equals("SunOS") ) {
classSeparator = ":" ;
} else {
classSeparator = ";" ;
}

return classSeparator ;
}
}

============================================================================

I'm trying to get it working in a more elegant way.
I realize that the code in the two classes is pretty much the same and
want to write a single class, which returns classpath and filepath
separators.

But, I dont see a way to return two strings.

a) Do I have to return an array? And then index out of this array to
get the classpath or filepath separators.

b) Can I write an object which holds these values and return that
object?
How do I then 'retrieve' any one single separator from the returned
values?

Could anyone please point me in the right direction.

Thanks for your time,
Reddy
 
C

Chris Uppal

Chris said:
It's hard to imagine why that's the case, but two possibilities spring
to mind. [...]

Or perhaps is experimenting with better (in the sense of better OO) ways of
doing this sort of thing than the horribly procedural approach that
System.getProperty() can encourage...

-- chris
 
C

Chris Uppal

Chris said:
class SystemInfo
{
private String fileSeparator;
private String classPathSeparator;

[... etc]

It might be worth going further in this direction.

A first step would be to make the constructor for SystemInfo do the test on
system type. Perhaps use a Singleton pattern for a slight improvement in
efficiency.

Second step; these things are going to be used to parse filenames. Why not
make that parsing the responsibility of that class, so that you (e.g) ask a
SystemInfo (or FilenameParser might be a better name) to split a path into its
segments. That way all filename parsing would be the responsibility of these
objects, rather than scattered ad-hoc over all the places where filenames are
used. Done that way, it's quite possible that you'd be able to get away
without even having accessors for fileSeparator and classPathSeparator.

For the OP: As an example of why this would be valuable, consider that people
tend to forget that '/' is a valid filename separator on Windows. If that
knowledge is embedded in the right object (the object with responsibility for
parsing filenames) then *all* filename-handling code gets it right. Without
that it's almost certain that someone somewhere in the app will have forgotten
to handle that case.

-- chris
 
C

Chris Smith

Chris said:
Second step; these things are going to be used to parse filenames. Why not
make that parsing the responsibility of that class, so that you (e.g) ask a
SystemInfo (or FilenameParser might be a better name) to split a path into its
segments. That way all filename parsing would be the responsibility of these
objects, rather than scattered ad-hoc over all the places where filenames are
used. Done that way, it's quite possible that you'd be able to get away
without even having accessors for fileSeparator and classPathSeparator.

It's worth noting, of course, that the java.io.File class is already an
implementation of this, so it's unlikely to be worth it to re-implement
the functionality unless you're adding something substantial over what
the standard File class does... and even then to consider working off of
what File provides as a basis for your implementation.

Even so, the ability to build a file parsing class doesn't conflict with
providing an object that collects system information. If retrieving
information about path separators is the goal, there's nothing wrong
with providing that, and then building other abstractions on top of it
as needed.

--
www.designacourse.com
The Easiest Way to Train Anyone... Anywhere.

Chris Smith - Lead Software Developer/Technical Trainer
MindIQ Corporation
 
C

Chris Uppal

Chris said:
Second step; these things are going to be used to parse filenames. Why
not make that parsing the responsibility of that class, [...]

It's worth noting, of course, that the java.io.File class is already an
implementation of this, so it's unlikely to be worth it to re-implement
the functionality

True. Though the functionality I was talking about is actually closer to what
the package-private helper class java.io.FileSystem and its subclasses do (in
Sun's implementation). I rather like that bit of the IO library's design.

Still, we're getting rather a long way away from the original question -- but
then, I think that's the point I was trying to make: starting from how *not* to
return two values from one method, we have ended up with an example of Good
Design.

-- chris
 
G

Gregory A. Swarthout

Chris Smith said:
No. I'm not familiar with the OP's situation, but since the post said
something like "for a variety of reasons, I can't use getProperty", I'd
say it's a safe bet that the OP probably shouldn't be using getProperty,
or at least isn't interested in hearing about it.

It's hard to imagine why that's the case, but two possibilities spring
to mind. Either: (a) the OP is implementing System.getProperty in a
clean-room implementation of the Java API, or (b) this is just an
example of a more general question about what to do with multiple return
values.

You've missed the most obvious and most likely one: (c) My instructor
wants us to implement this without using System.getProperty.

Greg
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
474,262
Messages
2,571,058
Members
48,769
Latest member
Clifft

Latest Threads

Top