views:

455

answers:

5
+5  Q: 

C# Partial Classes

I currently have a solution with multiple projects that mostly use the same classes. As a result, it appeared to me that it would be a good idea to add a class library containing these classes in the solution instead of repeating the class in each project.

However, one project I have requires a few additional properties to some of the classes that are specific to that project and will not be used anywhere else. As a result, I thought that I should use partial classes to add these properties. So I have done something like this:

In the class library:

namespace MyClassLibrary
{
    public partial class Book
    {
        public string Title { get; set; }
        public string AuthorLast { get; set; }
        public string AuthorFirst { get; set; }
        public string Publisher { get; set; }
        public string Edition { get; set; }
        public string ISBN10 { get; set; }
        public string ISBN13 { get; set; }
    }
}

In the project (MyProject):

namespace MyClassLibrary
{
    public partial class Book
    {
        public string AdditionalProperty { get; set; }
    }
}

I have referenced MyClassLibrary in MyProject (a C# windows form app), however when I try to use this class in the codebehind for the form I receive the following error:

class MyClassLibrary.Book

Warning: The type 'MyClassLibrary.Book' in 'C:... (Project)' conflicts with the imported type 'MyClassLibrary.Book' in 'C:... (Class Library DLL)'. Using the type defined in 'C:...(project)'.

Any idea what I am doing wrong or if my whole approach is bad and I should be doing something else?

+2  A: 

In short, you can't use partial classes across projects. All the source must be compiled at the same time, and that's done per project.

Here's a full discussion on SO about this: Should you use a partial class across projects?

Nick Craver
Thanks for the quick answer. Do you have any ideas how I may best organize the classes then given this issue? Should I just duplicate them in the projects or just add the property to the class in the class library even though its only for one project?Edit: am going to try derived classes as suggested below. thanks again
Andrew
I would go with Rex's answer for a solution, inheriting the classes seems like the best approach...unless there's a reason you can't, if so, what additional restriction is there?
Nick Craver
+11  A: 

Partials are not for spanning assemblies. If you need to add to your class for a more specific type of usage, you should create a derived class:

public class MyFoo
{
    public string BasicProperty {get;set;}
}

public class MySpecificFoo : MyFoo
{
    public string AnotherProperty {get;set;}
}

In your project requiring the more specific type of MyFoo, utilize MySpecificFoo instead. Since it inherits/derives from MyFoo, it will have all of the properties and functionality of MyFoo, with the additional properties as well. This is part of Polymorphism, which is where real power of OOP lies.

Rex M
thanks! i'll try it with a derived class... still new at this!
Andrew
uh...no, this is called "inheritance"!
Steven A. Lowe
@Steven edited for clarity
Rex M
+1  A: 

For what you're trying to do, you should instead try to use base classes and inheritance. Or even better object composition.

Dan Herbert
from the immediate description, composition is definitely not a better solution
Steven A. Lowe
@Steven Absolutely. I just find that it is helpful to point out because many novices learn about inheritance and then get themselves in trouble by using it **everywhere** simply because they don't know any better.
Dan Herbert
A: 

I think this is more along the lines of what you're trying to achieve.

Put all of your common classes into a class library project and compile it to a DLL.

You can then reference that DLL in external projects. Anytime you need to add a property to it for the external project you can then inherit the class and add the property there.

Chris Marisic
A: 

all wrong. You should consider partial methods instead. Look 'em up. They're exactly what you asked for.

No Refunds No Returns