Is this really more convenient than simply overriding toString() ?
- Mike
On Thu, 2004-10-07 at 09:45, Kris Schneider wrote:
> This should always give you the equivalent of Object's toString method:
>
> Integer.toHexString(System.identityHashCode(obj)).
>
> If anything gets added, I'd rather see something like what's used in
> java.awt.Component. The toString method is implemented like:
>
> public String toString() {
> return getClass().getName() + "[" + paramString() + "]";
> }
>
> Then Component has its own implementation of the paramString method:
>
> protected String paramString() {
> ...
> return str;
> }
>
> Finally, subclasses invoke super.paramString and add their own information:
>
> protected String paramString() {
> return super.paramString() + ...;
> }
>
> The implementation of paramString for ActionForm should probably just look
> like:
>
> protected String paramString() {
> return "";
> }
>
> ;-) About the only thing worth adding might be the ActionServlet reference. In
> the end, all this is doing is providing a convenient hook for subclasses. The
> decision about what information to include is still the responsibility of the
> subclasses (as it should be).
>
> Note that DynaActionForm already provides its own implementation of toString,
> which is inherited by DynaValidatorForm and DynaValidatorActionForm. So,
> DynaActionForm could then be changed to remove its toString method and provide
> a paramString method instead:
>
> protected String paramString() {
> StringBuffer buff = new StringBuffer();
> if (!this.dynaValues.isEmpty()) {
> buff.append(", ");
> for (Iterator iter = this.dynaValues().entrySet().iterator();
> iter.hasNext();) {
> Map.Entry entry = (Map.Entry)iter.next();
> buff.append(entry.getKey()).append("=");
> Object propValue = entry.getValue();
> if (propValue == null) {
> buff.append("<NULL>");
> } else if (propValue.getClass().isArray()) {
> buff.append("[");
> int length = Array.getLength(propValue);
> for (int i = 0; i < length; i++) {
> buff.append(Array.get(propValue, i));
> if (i < (length - 1)) {
> buff.append(", ");
> }
> }
> buff.append("]");
> } else {
> buff.append(propValue);
> }
> if (iter.hasNext()) {
> buff.append(", ");
> }
> }
> }
> return super.paramString() +
> ", dynaClass=" + getDynaClass().getName() +
> buff.toString();
> }
>
>
> Quoting [EMAIL PROTECTED]:
>
> > Frank,
> >
> > I also had to go a long way until I found this approach. It actually came to
> > me when I saw in my project many data objects (= java beans) were generated
> > using UML tools that did not care about the toString() method my way. Next I
> > saw Castor XML/JAXB and JDO code generation, and finally had to decide that a
> > common base class or implementing each and every toString method is not the
> > solution.
> >
> > With the static method I can apply my toString implementation to any object
> > that comes along - just what you need for debugging. I just wonder why the
> > Apache commons-beanutils does not provide such a method, and someone
> > mentioned it might be in commons-lang, but I could not find that either.
> >
> > Hiran
> >
> > -----------------------------------------
> > Hiran Chaudhuri
> > SAG Systemhaus GmbH
> > Elsenheimer Stra�e 11
> > 80867 M�nchen
> > Phone +49-89-54 74 21 34
> > Fax +49-89-54 74 21 99
> >
> >
> >
> >
> > > -----Original Message-----
> > > From: [EMAIL PROTECTED] [mailto:[EMAIL PROTECTED]
> > > Sent: Donnerstag, 7. Oktober 2004 14:22
> > > To: [EMAIL PROTECTED]
> > > Subject: RE: Proposed Action base class change
> > >
> > > Another fair point. :)
> > >
> > > Well, that's the reason I put the idea out there... I can't
> > > think of every possible angle to look at it from... If I
> > > thought I could, I wouldn't need to solicit opinions in the
> > > first place.
> > >
> > > Kind of depressing though... I'm trying to contribute, but so
> > > far all my ideas have been shot down (but for good reasons,
> > > so I'm not bitter about it). Just have to keep trying I suppose. :)
> > >
> > > --
> > > Frank W. Zammetti
> > > Founder and Chief Software Architect
> > > Omnytex Technologies
> > > http://www.omnytex.com
> > >
> > > On Thu, October 7, 2004 8:56 am, [EMAIL PROTECTED] said:
> > > > Hi, Frank.
> > > >
> > > > I do not agree. While in most cases it is desireable to see
> > > inside a
> > > > bean (hence I created my
> > > > public static String toString(Object bean) method),
> > > there are times
> > > > when I just have to make sure a bean is not just equal but the same
> > > > instance.
> > > > The java.lang.Object.toString() methods allows me to that quite
> > > > quickly as the memory address is printed.
> > > >
> > > > Unless you have another way to provide that information, I'd rather
> > > > stick with the default toString() plus some utility
> > > toString(Object)
> > > > method. The impact for you is not too much. What you code so far is:
> > > > log.debug("mybean="+mybean);
> > > > and you'd have to change that to
> > > > log.debug("mybean="+BeanUtil.toString(mybean));
> > > > which will allow you to either see the memory address or
> > > the contents,
> > > > whatever you prefer.
> > > >
> > > > Hiran
> > > >
> > > > -----------------------------------------
> > > > Hiran Chaudhuri
> > > > SAG Systemhaus GmbH
> > > > Elsenheimer Stra?e 11
> > > > 80867 M?nchen
> > > > Phone +49-89-54 74 21 34
> > > > Fax +49-89-54 74 21 99
> > > >
> > > >
> > > >
> > > >
> > > >> -----Original Message-----
> > > >> From: Frank W. Zammetti [mailto:[EMAIL PROTECTED]
> > > >> Sent: Donnerstag, 7. Oktober 2004 13:43
> > > >> To: Struts Developers List
> > > >> Subject: Re: Proposed Action base class change
> > > >>
> > > >> Hi Niall,
> > > >>
> > > >> I certainly agree it would not be possible to satisfy
> > > everyone, but
> > > >> seeing as the intrinsic toString() is all but useless (and
> > > people do
> > > >> generally expect that to be the case with many classes),
> > > why not give
> > > >> an implementation that is of at least some use to some people?
> > > >> Surely it would be better than what you get now? Obviously it's
> > > >> something many people will override, and that's of course
> > > the whole
> > > >> point of inheritance. But providing even a slightly more useful
> > > >> default implementation (and maybe telling people it's a
> > > basic default
> > > >> implementation so as to try and keep the flood of bugzilla
> > > requests
> > > >> to a
> > > >> minimum) seems to me like a good idea.
> > > >>
> > > >> I can't address your point about dynabeans because I haven't used
> > > >> them enough to be able to intelligently comment (which is to say I
> > > >> haven't used them at all! :) )... I wouodn't imagine some basic
> > > >> implementation would be too tough for them as well.
> > > >>
> > > >> In any case, I will look at the toString builders you mentioned...
> > > >> I've come to really like using the commons packages and I try to
> > > >> whenever I can. This would be a good case I think, if it
> > > doesn't get
> > > >> added as I proposed. I already have an ActionHelpers class with a
> > > >> bunch of similarly-themed static methods for use from Actions, so
> > > >> maybe it's time to do so for forms as well.
> > > >>
> > > >> --
> > > >> Frank W. Zammetti
> > > >> Founder and Chief Software Architect
> > > >> Omnytex Technologies
> > > >> http://www.omnytex.com
> > > >>
> > > >> Niall Pemberton wrote:
> > > >> > Frank,
> > > >> >
> > > >> > For me it wouldn't be any use unless it also handled
> > > >> DynaBeans. Even
> > > >> > then I'd end up overriding it because I have some
> > > formatting utils
> > > >> > which do dates, arrays and collections. Seems to me if
> > > we put it in
> > > >> > then we would end up with a monster trying to satisy
> > > >> everyones needs
> > > >> > and forever dealing with bugzilla requests for
> > > enhacements (someone
> > > >> > would want an i18n version!) - all just for debugging.
> > > >> >
> > > >> > The easiest thing is to just put all that code into a
> > > >> utility method -
> > > >> > that way its only a one liner in the toString() - even
> > > >> better if you
> > > >> > have your own "base" ActionForm that all you others derive
> > > >> from, then
> > > >> > its only in one place.
> > > >> >
> > > >> > Also, there are a set of "toString" builders in commons
> > > >> lang which you
> > > >> > might like to use - including a reflection one like yours:
> > > >> >
> > > >> >
> > > >>
> > > http://jakarta.apache.org/commons/lang/api/org/apache/commons/lang/bu
> > > >> i
> > > >> > lder/package-summary.html
> > > >> >
> > > >>
> > > http://jakarta.apache.org/commons/lang/api/org/apache/commons/lang/bu
> > > >> i
> > > >> > lder/ReflectionToStringBuilder.html
> > > >> >
> > > >> > Niall
> > > >> >
> > > >> > ----- Original Message -----
> > > >> > From: "Frank W. Zammetti" <[EMAIL PROTECTED]>
> > > >> > To: "Struts Developer" <[EMAIL PROTECTED]>
> > > >> > Sent: Thursday, October 07, 2004 4:29 AM
> > > >> > Subject: Re: Proposed Action base class change
> > > >> >
> > > >> >
> > > >> >
> > > >> >>Obviously I made a typo in the subject... this applies to the
> > > >> >>ActionForm base class.
> > > >> >>
> > > >> >>Did anyone have any comment on this? I've noticed a lack
> > > >> of activity
> > > >> >>on the list lately...
> > > >> >>
> > > >> >>
> > > >> >>>Hello all...
> > > >> >>>
> > > >> >>>I find myself all the time overloading toString() of my
> > > >> ActionForms
> > > >> >>>for
> > > >> >
> > > >> > debugging
> > > >> >
> > > >> >>>purposes, so I can easily dump the current state of the
> > > object. I
> > > >> >>>had
> > > >> >
> > > >> > been doing
> > > >> >
> > > >> >>>this for each ActionForm class, specifically for it, but
> > > >> it ocurrs to
> > > >> >>>me
> > > >> >
> > > >> > that a
> > > >> >
> > > >> >>>general-purpose reflection-based approach would be better.
> > > >> >>>
> > > >> >>>I'd like to propose adding this functionality to the
> > > >> ActionForm base
> > > >> >
> > > >> > class. Here's
> > > >> >
> > > >> >>>the code I propose adding:
> > > >> >>>
> > > >> >>>import java.lang.reflect.Field;
> > > >> >>>public static final AVERAGE_FIELD_SIZE = 25; public String
> > > >> toString()
> > > >> >>>{
> > > >> >>> String str = "";
> > > >> >>> StringBuffer sb = null;
> > > >> >>> try {
> > > >> >>> Field[] fields = this.getClass().getDeclaredFields();
> > > >> >>> sb = new StringBuffer(fields.length * AVERAGE_FIELD_SIZE);
> > > >> >>> for (int i = 0; i < fields.length; i++) {
> > > >> >>> if (sb.length() > 0) { sb.append(", "); }
> > > >> >>> sb.append(fields[i].getName() + "=" +
> > > fields[i].get(this));
> > > >> >>> }
> > > >> >>> str = sb.toString().trim();
> > > >> >>> } catch (Exception e) {
> > > >> >>> str = "Exception in ActionForm.toString() : " + e;
> > > >> >>> }
> > > >> >>> return str;
> > > >> >>>}
> > > >> >>>
> > > >> >>>The value of AVERAGE_FIELD_SIZE is a matter of debate,
> > > and it's of
> > > >> >
> > > >> > course impossible
> > > >> >
> > > >> >>>to come up with a real value, so something reasonable is
> > > >> the answer.
> > > >> >>>25
> > > >> >
> > > >> > struck me
> > > >> >
> > > >> >>>as a decent starting point.
> > > >> >>>
> > > >> >>>What does everyone think? I find this functionality to be very
> > > >> >>>useful
> > > >> >
> > > >> > in my work,
> > > >> >
> > > >> >>>and I suspect others may as well. The code doesn't add any
> > > >> >>>dependencies
> > > >> >
> > > >> > outside
> > > >> >
> > > >> >>>J2SE, and it's certainly simple enough as to not be
> > > >> particularly risky.
> > > >> >>>
> > > >> >>>Thanks all!
> > > >> >>>
> > > >> >>>Frank W. Zammetti
> > > >> >>>Founder and Chief Software Architect Omnytex Technologies
> > > >> >>>http://www.omnytex.com