This is a follow-up to my previous question Stop my "Utility" from giving errors between different architectures, suppose I am trying to create a class library that looks something like this:
- Class Utility (Parent class)
... Utility functions and methods
(EG: Public Sub Sub1() )
- Class Utility_Web
... Functions and methods only related to Web / Web-Controls
(EG: Public Sub Web_Sub1() )
- Class Utility_WinForms
... Functions and methods only related to Winforms / WinForm-Controls
(EG: Public Sub WinForm_Sub1() )
Now, what I would like to be able to do is to just add the Utility dll as a reference to any of my projects and be able to access the functions and methods from ALL 3 of these classes by simply typing in, for example:
Utility.Sub1
Utility.WebSub1
Utility.WinFormSub1
In other words, not having to type:
Utility.Utility_Web.Websub1
And making it so that the end-programmer doesn't need to know the internal structure of this utility, they can reference all it's methods / functions with just the Utility. nomenclature.
How would I go about doing that? Is this where NameSpaces come into effect? Inheritance? Partial Classes? Modules rather than classes?
There doesn't seem to be any reason for these methods to be in separate classes if they are going to be accessed using the same class name.
If you want to split the code across many source files for organizational purposes, you can use partial classes.
This seems like an excellent instance where you'd want to use partial classes, all using the same Utility namespace. That would allow you to access the methods with Utility.WebSub1 and reduce a step.
A class named Utility is a bad class from the start. What is its utility? What does it help you do? How many other people are going to name classes Utility?
Name your classes for what they do, associate them in the namespaces where they make logical and functional sense.
Let's say that you are making a set of static methods that help out with a class that represents a Month. Why not put the methods into Month? If you're writing methods to transform data from one representation to another, name it that way (ie, MonthDataTranslation).
Don't worry about typing on the part of your clients or your client code. Intellisense and the C# using statement mitigate that a great deal and given the choice between a badly named, nebulous Utility class and a long, well-named class, I will pick the latter every single time.
Related
I have multiple classes in 1 file. I have to put them all in 1 file because of company standards for the program I'm writing something for. Is there some way to only make 1 class in the file accessible?
Nobody needs to see the other classes.
Depends on the purpose. If the only "accessible" class would simply use the functionalities of the other classes, then that class needs to be public, and the rest could be private.
If you have properties in that classes which are types of the other, they cannot be private then.
If you are using any code reviewing tools like stylcop etc. then it will force you to have one class file with only one declared class over there. You can't get rid of this.
But since you are actively using only one class then there are couple of option you have :-
You can make you class private
Use different data structure like struct etc to remove the use of your additional classes.
I have to write large amount of code which is going to be used in three asp.net pages.
I want to know the key points so that I can decide whether I should create Static Helper class , or create base class for common codes.
I am agree that creating single helper class vs creating multiple helper classes must be a careful job depending on various things like performance etc.., but the question still remain same , you can think me as a smart coder that can create perfect number of helper classes.
I think I am going to use these code only from these three asp.net pages.
Thanks for all your answers friends, but I need more inputs, can you please send more specific points.
Thanks.
If it is code that is being shared by all three ASP.NET pages and not by other code, a baseclass is a good idea.
The code is not exposed to the 'outside world' (by making the methods protected) and you define a context in which the methods should be used. They can only be called from an ASPX page that defines trough inheritance that it is-a certain base type where the methods make sense. A Helper method could be called from everywhere in your code by just passing the right parameters, even if this is conceptual invalid.
If it's code that's going to be called from different places (for example a ValidateEmail function) then a static helper class could help.
But if you opt for the helper class, you still have to decide how many helper classes you are going to create. Dumping all your helper functions in one class is probably not a good idea from maintenance perspective.
Create a base page and inherit from that and then put your helper method and properties on the base page.
How should one structure their frequently used non-important functions (conversions, etc) in C# since everything must be contained in an object? Usually I take all these functions and put them in a static Utility class. Is this a good practice? How do most developers do it?
This tends to be what most developers end up doing, myself included.
The only pitfall is when you start having a massive set utilities that shouldn't really all belong together (conversion, database access, logging you name it...).
Try to structure these as different assemblies, so projects that do not need a set of utilities will not have to import a large set of extraneous code.
An elegant method for doing that in C# is using extension methods (Link). You can then only import the relevant namespace if you need your utility functions.
On the technical side this is basically just a static utility class as you described it, but in C# you get nice syntactic sugar for using them.
Depending on the particular need, I'll normally use a static structure or a registered service provider. For example, for logging, I'll normally use a service provider and a logging class with an interface or base logger type, and then in dev mode I'll register a message box provider so that I can see all the logged lines for a particular log level, whereas for getting a particular List.find predicate for an object list I'll build a utility class that has a static method which returns a type-appropriate predicate class.
I second the notion of using extension methods for this. I generally have classes, in a .Extensions namespace, like StringExtensions, IEnumerableExtensions, etc. Basically, I try and create a separate class for each logical grouping of functionality. Normally that means I group them by the type they extend, the type they produce, or the overarching feature they support (converting, formatting, etc).
As the Title says, I've got a multi-project solution.
I've got a "core" project that is loaded with most of the other projects.
So my question is this, I have a few utility functions such as FormatPhoneNumber(..) that I would like to be able to access in the following manner from anywhere.
(in Project_B which depends on Core)
string str = FormatPhoneNumber(inputString);
At worst, I suppose I could live with a qualifier of some sort:
string str = util.FormatPhoneNumber(inputString);
The best way of doing this is to create a dll project (maybe called something like "CommonCode"?), that you can then reference this dll from all of your other projects and access the classes and methods therein.
You will have to have some sort of "qualifier" (as you call it) somewhere, but to reduce the impact use the using statement at the top of each file, e.g.
using util;
If you really must have such utility functions (you know, you shouldn't, but sometimes it's the best/easiest solution), I suggest having them either in the Core (assuming that every single project is dependent on the Core anyway), or in a separate utility assembly. If you don't want to have a separate assembly lying around, consider using ILMerge.
The qualifier should be no problem at all. I suggest not putting unrelated function into an Utils class, but rather use e.g. a Formatting class for all formatting functions. On the other hand, as s_ruchit in the meantime suggested, extension methods (e.g. for the string class) might come in handy as well.
(Did I mention that this ยง%$& MarkDown editor does not allow typing an [at] symbol on a German keyboard layout, because it instead creates a blockquote? Sigh.)
Try creating your own util library.
Create a Class Library project and put your util classes in there.
I myself try to adhere a naming convention like [companyName].Util.[subdomain]
Your example would probably fit in my [CompanyName].Utils.StringHelpers
You would then create a static class StringHelper with a static method FormatPhoneNumber.
You will see that these personal libraries quickly grow bigger. By grouping them you don't have to load all your code if you only need a subset of functions.
Use an extension method to make it easier to call the method without using the class name.
public static class Util {
public static string FormatPhoneNumber(this string input) {
:
}
}
The method will now appear on every string object. You do not need to know which class it comes from. However, if the extension class is declared in another namespace, you must still import the namespace.
string formattedString = inputString.FormatPhoneNumber();
If you are using C# 3.0, you can bind them all into one single static class use them as Extension Methods.
There are no global functions in .NET, so you will have to put your utility functions into a class. You can make the methods static, so you can call them without having to instantiate the utility class:
public class Utility
{
public static string FormatPhoneNumber(string input)
{
...
}
}
// usage:
string output = Utility.FormatPhoneNumber(input);
Put these methods into your core library or a separate utility library that can be used (referenced) by all other libraries and applications.
You need to put the functions in static classes. You cannot avoid the qualification (there are no global functions in C#):
<%= Formatters.PhoneNumber(rawData) %>
The utility functions should be grouped as per normal methods: similar methods go together, unrelated methods should go into different classes (event with static classes aim for low coupling and high cohesion).
The assembly each belongs in should be obvious: formatting functions only used by the presentation layer (ASP.NET project itself) belong there. Truly common functions could go into core.
If the function you are implementing can only be used in context of your application, i would recommend you to place it into the Core assembly (under a separate namespace like "Utils" for example) or a new DLL library of your application solution.
Only if the function can be used across multiple projects it makes sense to create a utility library. But always keep in mind that a utility library only make sense if it's maintained regularly.
If you want all code to access these methods then go with extension methods, otherwise I would go with Util class in core assembly.
FWIW, if you follow a more formalised namespace as boris sugguests (recommended to avoid conflicts) you can abbreviate with the using keyword:
using Util = [CompanyName].Utils.StringHelpers;
I tend to follow the DRY principle and create an alias as soon as I need it more than once.
I'm working with a 3rd party c# class that has lots of great methods and properties - but as time has gone by I need to extend that class with methods and properties of my own. If it was my code I would just use that class as my base class and add my own properties and method on top - but this class has an internal constructor. (In my opinion it was short sited to make the constructor internal in the first place - why limit the ability to subclass?)
The only thing I could think of was to create method / properties on my class that simply called into theirs - but it's acres of code and, well, it just doesn't "feel" right.
Is there any way to use this class a base class?
You ask: "Why limit the ability to subclass?"
Because designing for inheritance is tricky, particularly if you're designing for other developers to inherit from your class. As Josh Bloch says in Effective Java, you should design for inheritance or prohibit it. In my view, unless you have a good reason to design for inheritance, you shouldn't do so speculatively.
Does the class implement an interface which you could also implement (possibly by proxying most calls back to an instance of the original)? There's often no really elegant answer here - and the best solution will depend on the exact situation, including what you're trying to add to the class.
If you're not adding any more state - just convenience methods, effectively - then extension methods may work well for you. But they don't change what data an object is capable of storing, so if you need to add your own specialised data, that won't work.
Sounds like a perfect application for extension methods:
MSDN extension method docs
"Extension methods enable you to "add" methods to existing types without creating a new derived type, recompiling, or otherwise modifying the original type. Extension methods are a special kind of static method, but they are called as if they were instance methods on the extended type. For client code written in C# and Visual Basic, there is no apparent difference between calling an extension method and the methods that are actually defined in a type."
If the class has an internal constructor, and there are no public constructors, then that suggests that the designers did not intend for it to be subclassed. In that case, you can use encapsulation, or you can use extension methods.
Only if your class lives in the same assembly as the class you want to inherit from. An internal constructor limits the concrete implementations of the abstract class to the assembly defining the class. A class containing an internal constructor cannot be instantiated outside of the assembly.
Resharper has a nice feature to create delegating members.
Here is a sample of what you can do with it. It takes a couple of seconds.
I will not discuss whether you can build your own Facade around that 3rd party class. Previous authors are right, the library could be designed in the way that will not allow this. Suppose they have some coupled classes that have singletons that should be initialized in specific order or something like this - there may be a lot of design mistakes (or features) that 3rd party developers never care about, because they do not suppose that you will use their library in that way.
But OK, lets suppose that building a facade is not an impossible task, and you have in fact only one problem - there are too many methods you have to write wrappers around, and it is not good to do this manually.
I see 3 solutions to address exactly that problem
1) I suppose that new "dynamic" types of .NET 4.0 will allow you to workaround that problem without having to write "acres of code"
You should incapsulate an instance of 3rd party class into your class as a privare member with dynamic keyword
Your class should be derived from Dynamic or implement IDynamicObject interface. You will have to implement GetMember/SetMember functions that will forward all calls to the encapsulated instance of 3rd party class
Well, c# 4.0 is a future, Let's see on other solutions:
2) Do not write code manually if you have significant number of public methods (say more then 100). I would write a little console app that uses reflection and finds all public members and then automatically generates code to call encapsulated instance. For example
public type MethodName(params)
{
this.anInstanceOf3rdPartyClass.MethodName(params);
}
3) You can do the same as 2, but with the help of existing reflection tools, for example RedGate .NET Reflector. It will help you to list all classes and methods signatures. Then, paste all this in Word and a simple VB macro will let you generate the same code as you could do in 2.
Remark: As soon as you are not copying the code, but only copying method signatures, that are publicly available, I don't think you will violate the license agreement, but anyway it worth to re-check