|
|
Hmm... strange - I've been to Bolivia, but I've never seen anyone call these monkeys "helper class" over there
Seriously:
Of course, if "helper classes" don't exist for you (because it's not a very descriptive term, or the GOF haven't written about it, or for whatever reason), this whole discussion is pointless.
We are a big screwed up dysfunctional psychotic happy family - some more screwed up, others more happy, but everybody's psychotic joint venture definition of CP blog: TDD - the Aha! | Linkify!| FoldWithUs! | sighist
modified on Thursday, May 15, 2008 5:20 PM
|
|
|
|
|
I'd say go for the first approach.
By using your "TargetBase" class (or ITarget iface), you can apply extra information on those instances later on if you need.
Eg,
ITarget dt = new DelegateTarget(target);
dt.Status = TargetStatus.New; // Im not saying that these properties applies in this context
dt.TimeToLive = 123; //just that you have the option to add extra info if you need
dict.add(source, dt);
By using the pure delegate approach you can never attach any metadata to your targets.
Except for using more dictionaries that carry the extra info for each delegate.
Maybe you don't need such features, but IMO: an interface approach is always easier to extend than a pure delegate approach.
And I think an interface approach is cleaner when it comes to semantics (this is ofcourse just my own take on it, others may not agree)
Eg, every class that implements "ITarget" (or inherits TargetBase) promises that its purpose is to do what the interface implies.
(ofcourse you can abuse it and implement it differently, but the semantics associated with your interface promises something)
While delegates are more "oh yeah, I just return something of the correct type" , there is not the same kind of promise attached to a delegate type.
modified on Thursday, May 15, 2008 7:24 AM
|
|
|
|
|
My debugger breaks for the below exception when trying to restore a database, because the database is in use. My question is, if I don't catch exceptions in my DatabaseHelper class, following what I believe to be good practice, then I should at least catch and publish the exception in clients of DatabaseHelper . However, these clients should know nothing of this FailedOperationException exception, so to catch it I would have to broaden my catch scope, which I believe is not good practice. What do I do?
Microsoft.SqlServer.Management.Smo.SmoExceptionType.FailedOperationException
|
|
|
|
|
You catch this in your database class. This is a specific database related problem - I would then throw this as a custom exception to the client applications, with details of this as the inner exception.
|
|
|
|
|
This is for a testing framework, so would you minimise custom exceptions and use one for multiple helper classes, or go with a tighter fit of one custom exception per helper class?
Also, I use DatabaseHelper in SelectionHelper, so using only one custom exception reduces the complexity of Russian Doll type exceptions. In SelectionHelper I wrap CLR exceptions, and just re-throw custom exceptions.
|
|
|
|
|
We tend to use exceptions based on logical areas.
|
|
|
|
|
I am busy with a new ConfigHelper class, and can't seem to decide on which approach to take. The class is responsible for adjusting the config table in two databases, control and test. My dilemma is whether I make ConfigHelper a static class, and tell it which database to access for each task, or use instance methods and have one instance for each database.
|
|
|
|
|
Out of the blue, use instances and specify table identification in constructor.
We are a big screwed up dysfunctional psychotic happy family - some more screwed up, others more happy, but everybody's psychotic joint venture definition of CP blog: TDD - the Aha! | Linkify!| FoldWithUs! | sighist
|
|
|
|
|
I face similar issues all the time and I've come to the conclusion that whenever this dillema comes up to always choose static. I've never regretted it.
"The great pleasure in life is doing what people say you cannot do."
- Walter Bagehot
|
|
|
|
|
Evolution of the project has driven me to instance methods. This enables injecting specific helper class instances as dependencies into larger composite objects with more task oriented sets of responsibilities, such as running an integration test. E.g. I have two ExportTest derived classes, one that produces the control output, and another that produces the test output, with very different implementations. However, the base ExportTest class provides all derived classes with a DatabaseHelper object built by a factory according to their needs.
Semicolons. the number one seller of ostomy bags world wide. - dan neely
|
|
|
|
|
Is it going to be something that like the .NET configuration classes is going to be a "quick and simple" solution so to speak, and are users / programmers going to have to access the methods quickly? If that's the case I'd lean towards a static approach.
If it's going deeper and more involved (i.e. more extensible) and likely to be in the foundations of the project so to speak then I'd go for instance methods because you can set them up and customise them and then everything on top accesses that.
If that made any sense at all?
I doubt it. If it isn't intuitive then we need to fix it. - Chris Maunder
|
|
|
|
|
In theory I'd say anything that has a central function and doesn't use instance specific variables should be static.
In practice, however, I usually go straight for instance implementation because you never know when you need to implement functionality which you can only access from an instance.
It's a pain to change all the previously written code from static to instance.
I had that problem several times already, for example I recently made a connection class and wanted to make it static because I wouldn't need several instances of it.
However, after implementing half the code I had to use classes/methods that could called from an instance so I had to change a lot of stuff.
|
|
|
|
|
So, you are writing code, or you are refactoring stuff and notice that you have the exact same code in different areas of the application. Suddenly you see an opportunity to refactor this code and extract it into a general function that can be called form multiple locations.
So, how many times do you need to see the same code before you decide to do this?
2, 3, 4, or more?
Just curious if there is a general consensus on this...
|
|
|
|
|
In my case that depends, if it a short 2-5 line code it may stay if there are 2-3 copies.
If it's a longer code 2 copies are enough to extract the code.
|
|
|
|
|
About the same for me.
Though, sometimes I stumble upon functionality where I quickly see it would be better to outsource it into another method, even if it only gets used a single time.
I tend to look through any long methods I wrote to check if there isn't anything I can outsource into helper methods.
|
|
|
|
|
I'm not sure if it's consensus or not, but there is the rule of three:
From Wikipedia, the free encyclopedia
Rule of three is a code Refactoring rule of thumb to decide when a replicated piece of code should be replaced by a new procedure. It states that you are allowed to copy and paste the code once, but that when the same code is replicated three times, it should be extracted into a new procedure. The rule was introduced by Martin Fowler in Refactoring and attributed to Don Roberts.
Duplication in programming is a bad practice because it makes the code harder to maintain. When the rule encoded in a replicated piece of code changes, whoever maintains the code will have to change it in all places correctly. This process is error-prone and often leads to problems. If the code exists in only one place, then it can be easily changed there.
Curiously enough, three is also how many licks it takes to get to the center of a Tootsie Pop.
BDF
A learned fool is more a fool than an ignorant fool.
-- Moliere
|
|
|
|
|
2 at most. (IMO Fowler is wrong on this topic).
I don't copy code if I can avoid it. Fewer lines of code is less hassle, so if I need something
in a second location, I refactor.
And dual use is not a necessary condition either, even a single use can be sufficient to trigger
a refactoring into a separate method; possible reasons: improved readability; unit testing;
possible future reuse; ...
The above holds for a single programmer. Teams of programmers may find it more difficult to apply.
|
|
|
|
|
To add to the previous two posts:
http://c2.com/cgi/wiki?RuleOfThree[^]
Before reading the associated discussions, I would have said "two". But now... as a rule of thumb, it can help to balance Copy+Paste vs. premature generalization.
My experience shows that generalizing something requires a much more complex contract, you have to clearly define error handling and odd cases that don't even occur in the two simple instances. Thus the generalized implementation (including it's contract, documentation requirements etc.) may well be more complex than the sum of the two simple instances.
So maybe make a guess at the "Total Cost of Ownership" plus cost of "acquisition of the shared implementation".
We are a big screwed up dysfunctional psychotic happy family - some more screwed up, others more happy, but everybody's psychotic joint venture definition of CP blog: TDD - the Aha! | Linkify!| FoldWithUs! | sighist
|
|
|
|
|
I have developed an application architecture and we are all using it here at my company. Problem is, some of the guys are having problems getting their heads around it and now I am having doubts myself. I will try and explain without rambling on too much.
What I have is a web service with methods similar to the following for marshalling data back and forth between the client and server:
public SimpleBusinessEntity Save(SimpleBusinessEntity entity);
All classes in the application derive from SimpleBusinessEntity. The only field that SimpleBusinessEntity contains is the EntityType field which is an enum value to determine its type i.e. Tariff, Contract
Using the base entity class means I don't have to create web methods for each type of entity i.e. SaveTariff, SaveContract etc. When the client sends an entity to a web method, I check the EntityType property of the SimpleBusinessEntity and then call the appropriate workflow class which will process that type of business entity i.e. TariffWorkflow. So the server-side TariffWorkflow class would have a method such as:
public TariffEntity Save(TariffEntity entity);
Do people on this forum use similar techniques? I have developed a number of applications using this technique and I think it works well. It is easy to maintain and enhance. The problem I have is explaining it to others and getting them to understand the concept. These are experienced people. Have I made it too complicated?
Thanks in advance,
Adam
|
|
|
|
|
Based upon your description appears fairly straightforward. What is it that they don't understand? Are they VB developers?
|
|
|
|
|
Thanks for your response.
Yes, we were all VB developers here. I moved over to c# about five or six years ago. Some of the others haven't been able to do this, so their c# exposure has been in fits and starts. Maybe I am just no good at explaining it.
Adam
|
|
|
|
|
Adam Jasper wrote: These are experienced people.
[rhetorical since the VB cat is out of the bag] Experienced in what, breathing? [/rhetorical]
Adam Jasper wrote: Have I made it too complicated?
No. But it's not object oriented because this:
Adam Jasper wrote: The only field that SimpleBusinessEntity contains is the EntityType field which is an enum value to determine its type i.e. Tariff, Contract
is not object oriented. However since your peers can't even understand what you are doing now they sure as hell would be totally lost if you implemented an object oriented solution so I guess that's not a consideration.
led mike
|
|
|
|
|
led mike wrote: is not object oriented. However since your peers can't even understand what you are doing now they sure as hell would be totally lost if you implemented an object oriented solution so I guess that's not a consideration.
Sorry led mike, you will have to explain that one to me, how is it not object oriented? SimpleBusinessEntity is an abstract class that has one property and a few abstract methods. All other classes derive from SimpleBusinessEntity because essentially every other business entity can be considered a simple business entity. Some processes only work with simple business entities using the EntityType property and the methods. How is that not object oriented? I am interested to know your thoughts.
Regards,
Adam
|
|
|
|
|
Adam Jasper wrote: Sorry led mike, you will have to explain that one to me, how is it not object oriented?
The answer to that question is to explain Object Oriented Design. Obviously I can't do that since entire books and web sites have been dedicated to that very explanation and still mostly fall short of giving any individual that knowledge. Perhaps it's because one person cannot give the understanding of OOD to another person. Perhaps understanding OOD must be arrived at by taking a journey down that path. Wow that was bunch of fluff eh?
A short statement I might make to even point you in a direction is that what you describe might be referred to as "using objects" as opposed to "object oriented". I know that probably doesn't help, but like I said, short of writing a book.
This is kind of weird since I just posted this[^] like 15 minutes ago
Also Web Services do not tend to be Object Oriented because of their remote nature they are generally a request-response oriented interface.
led mike
|
|
|
|