views:

152

answers:

4

Hey all,

I'm in the process of architecting a library that will be used in multiple releases of a product, and part of its job is to augment some of the functionality that doesn't exist in .NET 1.1, since we're required to use it. Probably the best example of this is the String.IsNullOrEmpty method, whose functionality we rely on fairly heavily.

The String class in .NET is sealed; I've thought about using either the Adapter or Decorator patterns to extend the functionality of the class by wrapping the original string, but I'm not convinced that this is a very intuitive approach for what I'm trying to do. I've also looked at another post on StackOverflow about a similar question, but it again raises the issue I just mentioned.

I could definitely use Adapter to create the functionality I'm looking for, but I can't imagine doing this for every string:

bool isEmpty = new StringExtensionAdapter(myXmlNode.SelectSingleNode(myXpathString)).IsNullOrEmpty();
if (isEmpty)
{
    // Do something
}

I don't necessarily dislike this approach, but it seems like it results in a lot of memory management where a different solution might be better. Also, I'm not crazy about creating a "StringUtility" library since that approach takes me further away from the object-oriented design I'd like to follow.

Any input would be helpful; if I'm just crazy and should use one of these approaches, let me know. I'm searching more for best practices than a solution, since I have several.

+2  A: 

By definition, there is no clean approach. I think the adapter approach is the best you can do in .NET 1.1. Of course, this will require you to go back and forth when dealing with the outside world.

Matthew Flaschen
+3  A: 

I would prefer the "StringUtility" library with a static IsNullOrEmpty method personally. In essence you would be creating extension methods without the nice syntax for calling them.

Dolphin
A: 

I agree with Matthew that there is no clean approach. The Decorator pattern is not applicable, since it relies on inheritance (or, at least, polymorphism), and you can't Decorate System.String, since you can't create a class that has the same interface (since it's sealed).

Adapter is basically used to Adapt one interface to another. That's not really what you want to do here. Essentially, what you seem to have in mind is a Wrapper, but as Matthew points out, you will have to convert back and forth a lot.

Perhaps you could name your new type "Text" and implement implicit conversions to and from string to minimize the amount of casts you will need to write. If you choose that route, make sure that you design your type as an immutable type, because that's the same behavior as strings themselves.

Mark Seemann
A: 

You can use an implicit operator to make things more "natural":

public class SuperString
{
    public SuperString(string s) { S = s; }

    public static implicit operator SuperString(string s)
    {
        return new SuperString(s);
    }

    public string S { get; private set; }

    public bool IsNot() { return String.IsNullOrEmpty(S); }
}

[TestMethod]
public void Test_SuperString()
{
    SuperString ss = "wee";
    SuperString xx = "";
    if (xx.IsNot()) ss = "moo";
    System.Console.WriteLine(ss.S);
}
Ray