Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Re: How is this "pattern" called?

30 views
Skip to first unread message
Message has been deleted

markspace

unread,
May 18, 2012, 11:29:56 AM5/18/12
to
On 5/18/2012 1:53 AM, Stefan Ram wrote:
> In the MVC pattern, I think, M, V, and C should be at least
> one non-innner class each?
>
> I often have seen (possibly, especially in beginner code) a
> coding pattern, where there is only one single non-inner class:
> the model.


"Especially in beginner code" seems to say to me that they might be
copying from beginner examples, especially of the sort that appear in
Oracle's Java tutorial. These example are designed to be shorter to
read on a web page or book page, and don't show best practice or correct
pattern. The examples simply show how to use the API.

Also, MVC is not MVC. That is, most languages and frameworks use a
modified MVC that really isn't MVC. Java itself uses a "split model"
design pattern. Model-Presenter-Controller is currently a popular
design pattern which can be used in Java.

<http://www.martinfowler.com/eaaDev/uiArchs.html>


>
> The listeners and the view then are embedded into this
> model, possibly, as inner classes. It's not really MVC
> as the observer pattern is not used for decoupling.


"Close coupling" is an anti-pattern in most cases.

Do you have an example we could look at?


markspace

unread,
May 18, 2012, 11:37:37 AM5/18/12
to
On 5/18/2012 8:29 AM, markspace wrote:
> design pattern. Model-Presenter-Controller is currently a popular design


Argh. Model-View-Presenter. How did I mix those up?


Jim Janney

unread,
May 18, 2012, 12:03:04 PM5/18/12
to
r...@zedat.fu-berlin.de (Stefan Ram) writes:

> In the MVC pattern, I think, M, V, and C should be at least
> one non-innner class each?
>
> I often have seen (possibly, especially in beginner code) a
> coding pattern, where there is only one single non-inner class:
> the model.
>
> The listeners and the view then are embedded into this
> model, possibly, as inner classes. It's not really MVC
> as the observer pattern is not used for decoupling.
>
> So, to code a simple Java-GUI application, one just writes
> a single class with the model and the controllers as inner
> classes and no observer pattern for model-view decoupling.
> Is there a name for this simple design?
>
> What about »the bulk-class pattern«? Or »the naive GUI pattern«?

Big Ball of Mud seems to fit:

http://laputan.org/mud/

--
Jim Janney
Message has been deleted

markspace

unread,
May 18, 2012, 1:35:47 PM5/18/12
to
On 5/18/2012 9:59 AM, Stefan Ram wrote:

> I do not see a real problem with this style, assuming that
> the assignment at hand was just to write such a simple dot
> paint program.


Right, though the style doesn't particularly teach best practice either.

I think I'd call this the "monolithic example" pattern. It's similar to
a lot of example code I see in books and the Java tutorial. It's
monolithic because it crams everything into a single class, or at least
into the minimum page space.

And it's an example because that's what it is. A short program that
isn't written by more than one person, and will not be maintained. It's
fine for what it is, but it's not an example of good production style
coding either.


Gene Wirchenko

unread,
May 18, 2012, 1:50:42 PM5/18/12
to
On Fri, 18 May 2012 10:03:04 -0600, Jim Janney
<jja...@shell.xmission.com> wrote:

>r...@zedat.fu-berlin.de (Stefan Ram) writes:
>
>> In the MVC pattern, I think, M, V, and C should be at least
>> one non-innner class each?
>>
>> I often have seen (possibly, especially in beginner code) a
>> coding pattern, where there is only one single non-inner class:
>> the model.

Beginner code does tend to be for a small system.

>> The listeners and the view then are embedded into this
>> model, possibly, as inner classes. It's not really MVC
>> as the observer pattern is not used for decoupling.
>>
>> So, to code a simple Java-GUI application, one just writes
>> a single class with the model and the controllers as inner
>> classes and no observer pattern for model-view decoupling.
>> Is there a name for this simple design?

How about "KISS"?

>> What about »the bulk-class pattern«? Or »the naive GUI pattern«?
>
>Big Ball of Mud seems to fit:
>
>http://laputan.org/mud/

If the ball is not big, then it is a case of KISS or maybe YAGNI.

There is little sense in using large system methodology on a
small system. (Do watch though that you do not keep adding to a small
system and switch over to having a large system wihtout realising it.)

Sincerely,

Gene Wirchenko

markspace

unread,
May 18, 2012, 3:20:11 PM5/18/12
to
On 5/18/2012 10:50 AM, Gene Wirchenko wrote:

> a case of KISS or maybe YAGNI.


I like these too; good thoughts.

John B. Matthews

unread,
May 18, 2012, 3:35:52 PM5/18/12
to
In article <MVC-20120...@ram.dialup.fu-berlin.de>,
r...@zedat.fu-berlin.de (Stefan Ram) wrote:

> I do not see a real problem with this style, assuming that the
> assignment at hand was just to write such a simple dot paint program.
>
> The inner classes can easily share a common model and identifier
> scope, while at the same time there is some reasonable separation
> between the different concerns of the inner classes.
>
> Should it be required later to decouple one of these inner classes
> more than now, this is also possible using a refactor that will make
> it become an outer class or will introduce an observer relationship.
> But should it not be required later, no time is wasted now to
> implement a decoupling and separation not needed.

I sometimes strive to make nested classes static in order to facilitate
re-factoring, as suggested in the example below. Static also keeps me
honest on inadvertent coupling. I also use the somewhat dated Observer
and Observable classes to stress the observer pattern, even implementing
Observer despite leaking `this`.

Here's my understanding of the basic architecture:

<http://stackoverflow.com/a/2687871/230513>

Here's a more elaborate example that mentions other ways to implement
the observer pattern:

<http://stackoverflow.com/a/3072979/230513>

And I frequently refer to this article on Swing & MVC

<http://java.sun.com/products/jfc/tsc/articles/architecture/>

import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Point;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.util.ArrayList;
import java.util.List;
import java.util.Observable;
import java.util.Observer;
import javax.swing.JFrame;
import javax.swing.JPanel;

public class MVCMain {

public static void main(String args[]) {
new MVCMain().buildGui();
}

public void buildGui() {
EventQueue.invokeLater(new Runnable() {

@Override
public void run() {
Model model = new Model();
View view = new View(model);
Control control = new Control(model, view);
JFrame f = new JFrame();
f.add(view);
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
f.pack();
f.setLocationRelativeTo(null);
f.setVisible(true);
}
});
}

private static final class Model extends Observable {

private List<Point> points = new ArrayList<Point>();

public void next(Point p) {
points.add(p);
setChanged();
notifyObservers();
}

public List<Point> getPoints() {
return points;
}
}

private static final class View extends JPanel implements Observer {

private Model model;

public View(Model model) {
this.model = model;
this.model.addObserver(this);
}

@Override
public void paintComponent(Graphics g) {
super.paintComponent(g);
g.setColor(Color.blue);
for (Point p : model.getPoints()) {
g.fillRect(p.x, p.y, 8, 8);
}
}

@Override
public Dimension getPreferredSize() {
return new Dimension(300, 300);
}

@Override
public void update(Observable o, Object arg) {
repaint();
}
}

private static final class Control {

private Model model;
private View view;

public Control(final Model model, View view) {
this.model = model;
this.view = view;
this.view.addMouseListener(new MouseAdapter() {

@Override
public void mousePressed(MouseEvent e) {
model.next(e.getPoint());
}
});
}
}
}

--
John B. Matthews
trashgod at gmail dot com
<http://sites.google.com/site/drjohnbmatthews>

Gene Wirchenko

unread,
May 18, 2012, 5:13:46 PM5/18/12
to
I have tended to avoid using OOP patterns except for what I came
up with myself. I did try reading one of the OOP patterns books, but
ugh! Some people seem to think that the last thing you should is do
in OOP is write a statement that actually instantiates an object.
(Qual horreur!) Instead, you call a factory -- is that it? -- and
have all sorts of indirection.

If you *really* need that, fine, but I do not. The closest that
I have come to this is related classes needing common code. I have
them inherit from a class with that code. That code class is never
instantiated itself.

With all of the hoopla over OOP patterns, it is difficult for me
to tell how much they are really needed.

Yes, I go for keeping it fairly simple.

Sincerely,

Gene Wirchenko

Patricia Shanahan

unread,
May 18, 2012, 5:35:57 PM5/18/12
to
I think a lot depends on the answer to one key question:

What is the cost if this needs to be changed?

If we are talking about a widely distributed API, where a change will
break thousands of programs, it is worth doing a lot to minimize the
risk of incompatible change. If we are talking about code that is used
in a couple of places in one program, KISS and refactor if necessary.

Patricia

markspace

unread,
May 18, 2012, 6:28:32 PM5/18/12
to
On 5/18/2012 2:13 PM, Gene Wirchenko wrote:

>
> I have tended to avoid using OOP patterns except for what I came
> up with myself. I did try reading one of the OOP patterns books, but
> ugh!
> ...
> If you *really* need that, fine, but I do not.


To me, this is the key part here. If you actually get the Gang of Four
book on patterns and read it -- and I mean read ALL of it, starting with
the front inside cover -- it says in the *introduction* not to use the
patterns exactly as presented, but to modify them to your particular
requirements. Patterns are there for you to get ideas from, but they
are not laws that must be followed with out deviation. You're still
required to think when using any given pattern.

In addition, with each pattern (that I've read, at least), the GOF
include a list of pro's and con's, and sometimes the cons are quite
surprising. For example the Visitor pattern doesn't work well when the
nodes/tree to traverse under goes lots of changes. The reason is that
the Visitor pattern isolates the implementation for each node, and it
can be a pain to go back into each implementation and add code for each
new type of node. They recommend not using the Visitor pattern at all
in this circumstance. Just use polymorphism and add the visitor API to
each node directly.

*That* is the biggest advantage to patterns and their study, imo. NOT
"rah rah yay patterns" but telling you when using a pattern might leave
you up a creek with no paddle. It allows you to eliminate a broad swath
of design space quickly and points you in a better direction.

Gene Wirchenko

unread,
May 18, 2012, 6:29:58 PM5/18/12
to
On Fri, 18 May 2012 14:35:57 -0700, Patricia Shanahan <pa...@acm.org>
wrote:

>On 5/18/2012 2:13 PM, Gene Wirchenko wrote:

[snip]

>> With all of the hoopla over OOP patterns, it is difficult for me
>> to tell how much they are really needed.
>>
>> Yes, I go for keeping it fairly simple.
>
>I think a lot depends on the answer to one key question:
>
>What is the cost if this needs to be changed?

Exactly.

>If we are talking about a widely distributed API, where a change will
>break thousands of programs, it is worth doing a lot to minimize the
>risk of incompatible change. If we are talking about code that is used
>in a couple of places in one program, KISS and refactor if necessary.

I quite agree with you.

With the amount of noise over patterns though, you would think
that many people need the patterns. For me, supporting an in-house
application, there is no or little need. I suspect that there are
many in my situation.

Sincerely,

Gene Wirchenko

Arne Vajhøj

unread,
May 19, 2012, 10:26:01 PM5/19/12
to
On 5/18/2012 4:53 AM, Stefan Ram wrote:
> In the MVC pattern, I think, M, V, and C should be at least
> one non-innner class each?

Yes.

Although sometimes the V is not a class but JSP/XHTML/FXML.

> I often have seen (possibly, especially in beginner code) a
> coding pattern, where there is only one single non-inner class:
> the model.
>
> The listeners and the view then are embedded into this
> model, possibly, as inner classes. It's not really MVC
> as the observer pattern is not used for decoupling.
>
> So, to code a simple Java-GUI application, one just writes
> a single class with the model and the controllers as inner
> classes and no observer pattern for model-view decoupling.
> Is there a name for this simple design?
>
> What about �the bulk-class pattern�? Or �the naive GUI pattern�?

I prefer "the big mess pattern".

:-)

Arne


Arne Vajhøj

unread,
May 19, 2012, 10:29:55 PM5/19/12
to
On 5/18/2012 12:59 PM, Stefan Ram wrote:
> final class Main
> {
> /* model */
>
> final private java.util.Collection<java.awt.Point> collection
> = new java.util.ArrayList<>();
>
> /* view */
>
> Panel panel;
> final private class Panel extends javax.swing.JPanel
> { public Panel()
> { this.setPreferredSize( new java.awt.Dimension( 300, 300 ));
> this.addMouseListener( new MouseListener() ); }
> final @java.lang.Override public void paintComponent
> ( final java.awt.Graphics graphics )
> { super.paintComponent( graphics );
> for( final java.awt.Point point : Main.this.collection )
> graphics.fillRect( point.x, point.y, 4, 4 ); }}
>
> final private class Frame extends javax.swing.JFrame
> { Frame()
> { Main.this.panel = new Panel(); this.add( Main.this.panel );
> this.setDefaultCloseOperation
> ( javax.swing.WindowConstants.DISPOSE_ON_CLOSE );
> this.pack(); this.setVisible( true ); }
> final @java.lang.Override public void dispose(){ super.dispose(); }}
>
> /* controller */
>
> final private class MouseListener extends java.awt.event.MouseAdapter
> { public final void mousePressed
> ( final java.awt.event.MouseEvent mouseEvent )
> { Main.this.collection.add
> ( new java.awt.Point( mouseEvent.getX(), mouseEvent.getY() ));
> Main.this.panel.repaint(); }}
>
> public final java.lang.Runnable buildGui = new java.lang.Runnable()
> { @java.lang.Override public final void run(){ new Frame(); }};
>
> public final void buildGui()
> { java.awt.EventQueue.invokeLater( this.buildGui ); }
>
> public static void main( final java.lang.String args[] )
> { new Main().buildGui(); }}
>
> I do not see a real problem with this style, assuming that
> the assignment at hand was just to write such a simple dot
> paint program.
>
> The inner classes can easily share a common model and
> identifier scope, while at the same time there is some
> reasonable separation between the different concerns
> of the inner classes.
>
> Should it be required later to decouple one of these inner
> classes more than now, this is also possible using a
> refactor that will make it become an outer class or will
> introduce an observer relationship. But should it not
> be required later, no time is wasted now to implement a
> decoupling and separation not needed.

From a theoretical point of view V and C are not part of M.

From the practical point of view the pattern (combined with
your non standard formatting) ensures that it takes 10
times longer to read and understand the code.

Arne



Arne Vajhøj

unread,
May 19, 2012, 10:33:01 PM5/19/12
to
True.

But separation of M, V and C seems to become relevant when
passing the 500 LOC mark.

Arne

Arne Vajhøj

unread,
May 19, 2012, 10:37:07 PM5/19/12
to
On 5/18/2012 5:13 PM, Gene Wirchenko wrote:
> On Fri, 18 May 2012 12:20:11 -0700, markspace<-@.> wrote:
>
>> On 5/18/2012 10:50 AM, Gene Wirchenko wrote:
>>
>>> a case of KISS or maybe YAGNI.
>
>> I like these too; good thoughts.
>
> I have tended to avoid using OOP patterns except for what I came
> up with myself.

That means that either you are absolute brilliant or a fool
not to learn from other.

> I did try reading one of the OOP patterns books, but
> ugh! Some people seem to think that the last thing you should is do
> in OOP is write a statement that actually instantiates an object.
> (Qual horreur!) Instead, you call a factory -- is that it? -- and
> have all sorts of indirection.

????

There are plenty of new'ing in patterns.

Some patterns with the purpose of making the client code
use different implementations use factories. Obviously since
new does not meet the requirement for enabling the use of
different implementations.

> With all of the hoopla over OOP patterns, it is difficult for me
> to tell how much they are really needed.

Almost all Java code uses various well defined patterns. Large parts
of both Java SE and Java EE uses them.

Arne

Arne Vajhøj

unread,
May 19, 2012, 10:38:04 PM5/19/12
to
On 5/18/2012 6:29 PM, Gene Wirchenko wrote:
> With the amount of noise over patterns though, you would think
> that many people need the patterns. For me, supporting an in-house
> application, there is no or little need.

Or you have not realized the need.

Arne

Lew

unread,
May 20, 2012, 2:34:27 PM5/20/12
to
Or both of you are looking at it from the wrong perspective.

I would bet that both of you use "patterns" in the larger, non-buzzwordy
sense, that is, you recognize the shape of structures in your model and can
exploit common idioms for common shapes. Both of you appear to be competent
programmers from what this newsgroup shows, and programmers become competent
only if they have that skill.

The argument is over "patterns" in the GoF sense, a highly bureaucratized,
overly-verbose and religiously canonical set of labels and formats to describe
them. But even amidst all the sturm und drang over the latter kind of
patterns, they provide value in a common terminology and informal use. So when
we discuss Visitor or Singleton, we all know what we mean. ("We" being
competent programmers. One occasionally sees posters here who are less
knowledgeable.)

I favor having a library of common pattern labels to facilitate both
communication and program design. No one should think that the list in
GoF-land is exhaustive, and certainly not mandatory. Just because you haven't
used one of the patterns from the Official List doesn't mean you don't need
patterns, or don't use them.

The point of the Official List is to identify some (only some!) of the most
common patterns and get us used to thinking in terms of patterns, not to be
set upon an altar and have thurifers waved at them.

--
Lew
Honi soit qui mal y pense.
http://upload.wikimedia.org/wikipedia/commons/c/cf/Friz.jpg

Arne Vajhøj

unread,
May 20, 2012, 2:59:46 PM5/20/12
to
????

I don't think anyone suggested to treat patterns religiously. What is
it that you call arguments against something that no one has actually
suggested?

There are no official list. There are multiple lists: GoF which
are somewhat general OOP, specific Java EE etc..

The common terminology is one of the benefits.

The other big benefit is to learn from others experience instead
of spending a decade or more to learn it the hard way. That point
is actual very much emphasized in the GoF book.

Arne


Patricia Shanahan

unread,
May 20, 2012, 3:03:07 PM5/20/12
to
On 5/20/2012 11:34 AM, Lew wrote:
...
> The argument is over "patterns" in the GoF sense, a highly
> bureaucratized, overly-verbose and religiously canonical set of labels
> and formats to describe them. But even amidst all the sturm und drang
> over the latter kind of patterns, they provide value in a common
> terminology and informal use. So when we discuss Visitor or Singleton,
> we all know what we mean. ("We" being competent programmers. One
> occasionally sees posters here who are less knowledgeable.)
...

I think the terminology point is very important. Saying "This is a
Singleton class" conveys a lot of information very compactly.

I do flip through GoF when I am looking for ideas of how to structure
something. Often, either one of the patterns fits or at least the idea
behind the pattern is useful to me. It's a useful catalog of alternatives.

Patricia

markspace

unread,
May 20, 2012, 4:19:14 PM5/20/12
to
On 5/20/2012 11:34 AM, Lew wrote:
> No one should think that the list in
> GoF-land is exhaustive, and certainly not mandatory.


I'm sure no one does. In support of this idea, I'll offer a couple of
good finds by Y.T. First, xUnit Test Patterns by Meszaros, an absolute
seminal work on test patterns for all you TDDers out there.

<http://www.amazon.com/xUnit-Test-Patterns-Refactoring-Code/dp/0131495054>

The other is Refactoring by Martin Fowler. It's organized as patterns
of change, ways that you can modify your code to improve it. The
organization into is useful because it gives each type of change an
distinct and succinct name, which facilitates communication. For
example, several of Fowler's patterns appear on the NetBeans "Refactor"
menu, and do exactly what he describes.

<http://www.amazon.com/Refactoring-Improving-Design-Existing-Code/dp/0201485672>

Gene Wirchenko

unread,
May 20, 2012, 11:40:00 PM5/20/12
to
On Sat, 19 May 2012 22:38:04 -0400, Arne Vajhøj <ar...@vajhoej.dk>
wrote:
Consider the possibility that the need might not be there at all.
I need to do X. I can do X simply with Y. What need of patterns
then?

Sincerely,

Gene Wirchenko

Gene Wirchenko

unread,
May 20, 2012, 11:43:45 PM5/20/12
to
On Sat, 19 May 2012 22:37:07 -0400, Arne Vajhøj <ar...@vajhoej.dk>
wrote:

>On 5/18/2012 5:13 PM, Gene Wirchenko wrote:
>> On Fri, 18 May 2012 12:20:11 -0700, markspace<-@.> wrote:
>>
>>> On 5/18/2012 10:50 AM, Gene Wirchenko wrote:
>>>
>>>> a case of KISS or maybe YAGNI.
>>
>>> I like these too; good thoughts.
>>
>> I have tended to avoid using OOP patterns except for what I came
>> up with myself.
>
>That means that either you are absolute brilliant or a fool
>not to learn from other.

You are missing the possibility that they are not needed. I do
not like overcomplicating my code. I like to keep it simple since I
am probably the one who will have to modify it in the future.

If a pattern works for me, fine, I will use it. If I do not need
it, then I will not use it.

I am not against patterns; I am against their use everywhere
regardless of circumstances.

[snip]

Sincerely,

Gene Wirchenko

Gene Wirchenko

unread,
May 20, 2012, 11:44:46 PM5/20/12
to
On Sat, 19 May 2012 22:33:01 -0400, Arne Vajhøj <ar...@vajhoej.dk>
wrote:

>On 5/18/2012 1:50 PM, Gene Wirchenko wrote:

[snip]

>> If the ball is not big, then it is a case of KISS or maybe YAGNI.
>>
>> There is little sense in using large system methodology on a
>> small system. (Do watch though that you do not keep adding to a small
>> system and switch over to having a large system wihtout realising it.)
>
>True.
>
>But separation of M, V and C seems to become relevant when
>passing the 500 LOC mark.

See? You agree with me. Different sizes of systems need
different methodologies.

Sincerely,

Gene Wirchenko

Lew

unread,
May 21, 2012, 3:09:54 AM5/21/12
to
Gene Wirchenko wrote:
> Arne Vajhøj wrote:
>> Gene Wirchenko wrote:
>>> markspace wrote:
>>>> Gene Wirchenko wrote:
>>>>> a case of KISS or maybe YAGNI.
>>>
>>>> I like these too; good thoughts.
>>>
>>> I have tended to avoid using OOP patterns except for what I came
>>> up with myself.
>>
>> That means that either you are absolute brilliant or a fool
>> not to learn from other.
>
> You are missing the possibility that they are not needed. I do
> not like overcomplicating my code. I like to keep it simple since I
> am probably the one who will have to modify it in the future.
>
> If a pattern works for me, fine, I will use it. If I do not need
> it, then I will not use it.
>
> I am not against patterns; I am against their use everywhere
> regardless of circumstances.
>
> [snip]

A 'for' loop is a pattern. A 'try-catch' idiom that reliably closes an
external resource (e.g., 'Reader' or 'Writer') in the same way each time you
write one is a pattern. Putting your member declarations in a certain order is
a pattern. Are you seriously suggesting that you have written non-trivial code
that is devoid of patterns?

If so, you are lying.

Lew

unread,
May 21, 2012, 3:11:23 AM5/21/12
to
Gene Wirchenko wrote:
> Arne Vajhøj wrote:
>> Gene Wirchenko wrote:
>
> [snip]
>
>>> If the ball is not big, then it is a case of KISS or maybe YAGNI.
>>>
>>> There is little sense in using large system methodology on a
>>> small system. (Do watch though that you do not keep adding to a small
>>> system and switch over to having a large system wihtout realising it.)
>>
>> True.
>>
>> But separation of M, V and C seems to become relevant when
>> passing the 500 LOC mark.
>
> See? You agree with me. Different sizes of systems need
> different methodologies.

Two smart people agree on something that is true. Amazing.

Gene Wirchenko

unread,
May 21, 2012, 1:04:35 PM5/21/12
to
I have been referring to OOP patterns.

>If so, you are lying.

More than a bit strong of language.

Sincerely,

Gene Wirchenko

Wanja Gayk

unread,
May 30, 2012, 8:32:51 AM5/30/12
to
In article <jp619l$5ms$1...@dont-email.me>, -@. says...

> Right, though the style doesn't particularly teach best practice
> either.
>
> I think I'd call this the "monolithic example" pattern.

That pattern is known as "god class".

> It's similar to
> a lot of example code I see in books and the Java tutorial. It's
> monolithic because it crams everything into a single class, or at least
> into the minimum page space.
>
> And it's an example because that's what it is. A short program that
> isn't written by more than one person, and will not be maintained. It's
> fine for what it is, but it's not an example of good production style
> coding either.

As a Java/Swing developper with almost a decade of experience, having
seen a lot of code that got refactored inside out and back again, It's
not that simple to say sonmething is good or bad. It depends on the
purpose.

For the start it's a pragmatic, yet entirely easy to refactor approach
that has one goal in mind: Keep a unit/module together.
I do agree that you should tear this apart into several classes, but to
understand why, let me start to develop the idea.

It all starts with one decision: Will we ever exchange view technology
(like Swing to SWT)? You can't know, so you should be flexible, right?
Wrong! I have yet to see one big project, huge as a retail system,
migrate from one view technology to the other. People don't do it, it's
massively expensive and they rather pay to keep the old technology alive
and patched than to migrate to a new one. So don't expect insurance
companies and warehouse chains to migrate a huge in house application
from Swing to SWT, JavaFX 2.0 or a web interface anytime soon. Things
are that complex and there are so many framework specific hacks involved
that migrating is a daunting task that only very few companies are
willing to pay for. Usually there have been a lot of developers on the
project, some of them good, some of them rather bad, you will dig out
big piles of code that hurts your eyes (and your code will hurt theirs)
and you'll have to untangle some huge mess before you can even start to
think about that. Don't do it.
Do we need flexibility here? Rather not.

It needs a very good framework to separate the concerns good enough to
ease the pain (I'm glad I had the opportunity to work on one as
framework-developper and user) of switching from Swing to SWT alone,
still it is a heavy task. Basically that framework has to have an own
abstraction for every widget that talks to the original Swing-Widget,
Abstractions for teh EventQueue and so on, so the GUI technology can be
replaced rather easily. Most smaller businesses don't have that, they
simply can't afford to build and maintain a huge ass framework like
that. So what they do is buy one. Then you'll have to stick to its rules
anyway, which some developers wil happily ignore, which is where your
problem will resurface. Forget it, quite frankly.

So here we are again: Average company, no special framework involved,
time pressure is on, external developers going in and out all the time.
What you need is some kind of clear structure and everything should be
easy to find. You don't want to spread one module (like the mask for
editing an article) over a huge class hierarchy with too many small
classes cluttering up your directories, so no one finds anything.

Now here's where it starts to get intersting, because you can approach
it differently. Most of you will know the web developer world, but let
me use a usual fat client example here, as this is what the example
seemed to suggest.

What do you need in general?

* You have a view

* You have some business logic, some of that will reflect in the way the
view behaves (no mail order -> mail service combobox not editable), some
of that will not (posting an order takes something off the stock, puts
it into the delivery queue and sends a confirmation email, whatever).

* You have validation, both for the view (name must be entered) and for
the businsss logic (item is out of stock, another user just ordered it
the second you klicked to send your order).

You need to glue that together, which is what the controller does, and
you need to embed all this in some application frame.

So a pragmatic approach is to have a module class, say the "article
module", which includes some value object for what's currently
displayed/edited - and that's not necessarily what you need to give the
widget: You like to validate and store a list, not a table model / you
like to have some booleans, not a button model.
Now you need some view, a validation code block and some code to CRUD
things in the database, if you need one.

To keep the module API small, it should not feature much more than
necessary to incorporate the module in the application frame,
initialize, display and tear it down again, everything else is "internal
affairs".

Next decision: Do you want to use a GUI-Designer like JFormDesigner?
Probably yes.
So you should have an own class for the widgets and their layout.

Now you don't want to access each field individually, so you would
probably hand over a copy of the value object to the view, so it can do
with it whatever it wants without affecting anything. You need to have
some event handling to get to know that some thing has changed in the
view that you might need to validate, do you?
Now you have the option to move some validation into the view, because
it's its internal affair, but that could get you into problems with re-
generating a GUI class. And GUI-Designer code is usually huge and
verbose and you don't want to edit that class manually and you don't
want ot to hide and obscure code relevant for business. So you could
keep it in the controller. For the same reason you possibly like to have
the code for binding a widget to a property in the value object in the
value object itself.

You have now split the module into two top level classes: A presenter
and a view. The rest is inner classes.

You could be fine here, this is almost what you see above, only with
some tweaking for use with a GUI designer tool.

Next decision: Do you want ORM-mapping for your persistence?
If so, you need an entity class. And you need some code that transfers
your value object's data to the database. Or you use the entity itself
as vaue object (which is a nice idea at first, but may fall on your feet
later, especially when you encounter things like a manual undo).

So you have three top level classes: A presenter, a view and an entity.

Next decision: Do you want client/server separation and do you need some
stiffer security?
This is an important decision, and for a huge business application it
would be a clear yes most of the times.
I've also seen a domain driven design, where you actually had business
logic and validation in the entities itself, which also served as value
objects for the view, so the client was doing all the business logic and
the server was just a database with some client logon/logoff and
permission stuff. Not what you would call hard to attack for anyone who
gets access to the client, but certainly enough for in house use on an
intranet in a small company and it was very clear where to find what.

If you want to separate client/server, you need some class to host the
web services for that module on the server side.
You will need to move some validation there - the stuff that is not
directly reflected in the GUI. This is the point where you will repeat
some of the validation from the GUI to be sure no one sends some weird
data from a modified client. And you will need to push some business
logic here, because sending mail for example, and changing the stock, is
not anymore client's business.

So now you have four top level classes: Presenter, View, Web Service,
Entity.
And you will have them in two different projects:
A "server" project and a "client" project.

Now let's go and solve the DRY-Principle that you have violated when
pushing the validation into the text field:
Your view would check a number field to highlight a value out of bounds,
your webservice would check it to throw an exception.
There you can move your validation to a top level class and put it into
a "common" project that is both included in the classpath of the client
and server. Since the client and the server both have their own class
loaders, you can't just simply modify the validator on the client side,
the server would still see his version of the class, so that practice is
safe enough to go with. You will need to move the business rules there
too, because you need them for validation and you don't want to make a
web service call everytime you change a combobox value in the view.
Be aware though, that this will violate the SOA (Service Oriented
Architecture) that you have just established by introducing the web
service.

If you really need SOA at this point, you need to bite the bullet and
either live with a lot of web service calls and kill your user
experience with sluggish behavior or violate DRY.

Anyway, for your module you might have five top level classes now:
Presenter, View, Web Service, Validator, Entity.

This is not quite "model view controller", but still a reasonable
architecture.

What do you think?

Kind regards,
-Wanja-

--
..Alesi's problem was that the back of the car was jumping up and down
dangerously - and I can assure you from having been teammate to
Jean Alesi and knowing what kind of cars that he can pull up with,
when Jean Alesi says that a car is dangerous - it is. [Jonathan Palmer]

--- Posted via news://freenews.netfront.net/ - Complaints to ne...@netfront.net ---

Wanja Gayk

unread,
May 30, 2012, 8:32:52 AM5/30/12
to
In article <z_CdncDz595QXSvS...@earthlink.com>,
pa...@acm.org says...

> > With all of the hoopla over OOP patterns, it is difficult for me
> > to tell how much they are really needed.
> >
> > Yes, I go for keeping it fairly simple.
>
> I think a lot depends on the answer to one key question:
>
> What is the cost if this needs to be changed?

It's rather two questions:

1. What is the cost if this needs to be changed?
2. What are the chances that we need to change this?

If the chances are low it can be more expensive. If the chances are
high, because this part is important, you better be flexible.

> If we are talking about a widely distributed API, where a change will
> break thousands of programs, it is worth doing a lot to minimize the
> risk of incompatible change. If we are talking about code that is used
> in a couple of places in one program, KISS and refactor if necessary.

Absolutely.

Wanja Gayk

unread,
May 30, 2012, 8:32:54 AM5/30/12
to
In article <jpbdfd$2rk$1...@news.albasani.net>, no...@lewscanon.com says...
>
> Arne Vajhøj wrote:
> > Gene Wirchenko wrote:
> >> With the amount of noise over patterns though, you would think
> >> that many people need the patterns. For me, supporting an in-house
> >> application, there is no or little need.
> >
> > Or you have not realized the need.
>
> Or both of you are looking at it from the wrong perspective.
>
[..]
> The argument is over "patterns" in the GoF sense, a highly bureaucratized,
> overly-verbose and religiously canonical set of labels and formats to describe
> them. But even amidst all the sturm und drang over the latter kind of
> patterns, they provide value in a common terminology and informal use. So when
> we discuss Visitor or Singleton, we all know what we mean. ("We" being
> competent programmers. One occasionally sees posters here who are less
> knowledgeable.)

I guess that's one of the most common misconceptions. Some people seem
to think that patterns are used, because they are considered cool and
fancy. While in the real world you use any certain pattern because and
only when it solves your problem.

I have seldomly seen a visitor pattern in the wild, because there are
not so many occasions where it's so considerably better than something
that is easier to understand to make it worth using.
But the strategy pattern is used everywhere, everytime you use a
Comparator for example, simply because it solves a very common problem
very well.

Wanja Gayk

unread,
May 30, 2012, 8:33:04 AM5/30/12
to
In article <96ejr7hcmgv68n2it...@4ax.com>, ge...@ocis.net
says...
Let me give you an example:

You copy and modify your sorting routine for each class you like to
sort, everywhere you need it. Simple, easy, does it:

for (int i = 1; i < articles.size(); i++){
int j = i;
final Article actual= articles.get(i);
while (j>0 && articles.get(j-1).getAmount() > actual.getAmount())){
articles.set(j, articles.get(j-1));
j--;
}
articles.set(j, actual);
}

[..]

for (int i = 1; i < articles.size(); i++){
int j = i;
final Article actual= articles.get(i);
while (j>0 && articles.get(j-1).getPrice() > actual.getPrice())){
articles.set(j, articles.get(j-1));
j--;
}
articles.set(j, actual);
}

It works, it is straightforward, so what?

If you use the strategy pattern and instead of copying and modifying the
sorting routine, just have one sorting method in a utility class, that
you need to call, provide it with a list and a comparison strategy
(Comparator):

class SortUtil{
public static <T> sort(final List<T> items,
final Comparator<? super T> strategy){
for (int i = 1; i < items.size(); i++){
int j = i;
final T actual= articles.get(i);
while (j>0 && strategy.compare(items.get(j-1), actual) > 0){
items.set(j, items.get(j-1));
j--;
}
items.set(j, actual);
}
}
}

You then define your comparison strategy and put it somewhere where it's
easy and intuive to find:

class Article{

public static Comparator<Article> COMPARE_BY_AMOUNT
= new Comparator<Article>(){
public int compare(Article a, Article b){
return a.getAmount() - b.getAmount(); //I know it stinks of overflow!
}
};

[..]

public static Comparator<Article> COMPARE_BY_PRICE
= new Comparator<Article>(){
public int compare(Article a, Article b){
return (int)(a.getPrice() - b.getPrice()); //I know it stinks hard!

}
};
}

That might look complicated first, but there is a huge benefit:
Wherever you sort articles, the result is quite readable:

SortUtil.sort(articles, Article.COMPARE_BY_AMOUNT);
SortUtil.sort(articles, Article.COMPARE_BY_PRICE);

Yes, you can also have that if you have a lot of copied methods like
this:
sortArticlesByAmountAsc(articles);
sortArticlesByPriceAsc(articles);

But the huge difference is: If you find an error in your sorting
routine, or if you want to change your sorting routine from insertin
sort to quicksort, you only need to fix it in one place and every code
that ises it will be fixed and sped up immediately.

You don't need to hunt down every copy that you have made (you will
forget one for sure) and apply the same change to all of them (you will
make a mistake somewhere). And since code evolves the fix might look
different everywhere, so searching for the code you need to change is
doomed to miss some occurrences.

Also you can easily re-use the comparison strategy, because is not
buried under a load of sorting loopcode, but seperate from it. You can
use it to compare two articles:

if(Article.COMPARE_BY_PRICE.compare(a1, a2)){
highlightError(articleChoiceA);
}

Now imagine your code review shows that the code stinks as the price is
of type "double", and you need to change that for "BigDecimal", then you
can fix the Comparator once and every part of your code that uses it
instantly works - so you have saved yourself a lot of time.
You did not need to hund down every sort routine you have copied and
modified, not even search for the compiler errors in simple if-clauses
where you had a < > operator first.

And since you know the Java-API, you also know that Collections.sort()
was built the same way. For a good reason.

Wanja Gayk

unread,
May 30, 2012, 5:58:51 PM5/30/12
to
In article <u9ejr71ed5r1jqf2e...@4ax.com>, ge...@ocis.net
says...

> If a pattern works for me, fine, I will use it. If I do not need
> it, then I will not use it.

Who does anyway?

Lew

unread,
Jun 2, 2012, 12:25:10 PM6/2/12
to
Someone who has actually read up on patterns will find that every pattern
document includes the motivation or scenarios for which the pattern applies.
No pattern is claimed to be universally applicable, or offered as "cool", but
always as relevant for a particular type of situation.

Part of knowing about patterns is learning to discern when one is useful and
when it isn't.

Any competent programmer who claims not to use patterns is lying, or at best
being disingenuous. One might not use them literally in the GoF style, but
they are there. As others in this thread have pointed out, if you program for
Swing or use almost anything in the standard API, you're using patterns even
if only those imposed on you by the API writer (e.g., MVC). Patterns in the
general sense are at the heart of effective programming. (Patterns in the
formal, strictly GoF-imitative sense not so much.)
0 new messages