Reputation: 14102
Lets say I have a class A
which is going to be compiled into a dll
to be used later. But I kind of know that later, some methods of class B
which I am not aware of its type must be called in A
class. The only clue is the name of the methods.
Lets say this is class A
:
public class A
{
A(Object instanceOfClassB)
{
//stuff...
}
public void SendProcessedString()
{
//some strings has been processd, I know that class B is going
//to have a public method like ReceiveData(string data){/*---*/}
instanceOfClassB.ReceiveData(data);
}
}
Lets say this is class B
, happen to be a WinForm:
public B : Form
{
public void ReceiveData(string data)
{
textBox.Append(data + Environment.NewLine);
}
}
Is such approach possible/recommended?
Upvotes: 0
Views: 93
Reputation: 33738
Yet another method is to use a proper callback - only if a single subscriber is guaranteed. If you need multiple subscribers use an event.
public class classA {
public Action<string> DataReceivedCallback = null;
public void SendProcessedString() {
if (null != DataReceivedCallback) { DataReceivedCallback.Invoke(data); }
}
}
somewhere in classB
instanceA.DataReceivedCallback = new Action<string>(dataReceivedHandler);
private void dataReceivedHandler(string data) {
// do something with the data.
}
Upvotes: 1
Reputation: 33738
Another option here would be to use events. Have your raise an event instead of invoking the callback.
excuse my C#, I'm a little rusty
public class classA {
public event DataReceived(string data);
public void SendProcessedString() {
// you got var data from somewhere
DataReceived(data)
}
}
Then subscribe to that event from your classB
// classB setup code or initializer:
instanceA.DataReceived += dataReceivedHandler;
private void dataReceivedHandler(string data) {
// do something with the data.
}
Upvotes: 2
Reputation: 2724
It sounds you need to use an interface
.
A little information about interfaces
can be found here.
Basically you want to create an interface
and get it as a parameter for class A
and implement it in class B
:
interface IDataReceiver
{
void ReceiveData(string data);
}
then class B
decleration will look like:
public B : Form, IDataReceiver
And class A` constructor:
A(IDataReceiver dataReceiver)
{
//stuff...
}
Upvotes: 2
Reputation: 1442
You should be using interface. You class B must implement "MyInterface" interface and "MyInterface" should have method which are are expecting A to call.
public class A
{
A(MyInerface instanceOfClassB)
{
//stuff...
}
public void SendProcessedString()
{
//some strings has been processd, I know that class B is going
//to have a public method like ReceiveData(string data){/*---*/}
instanceOfClassB.ReceiveData(data);
}
}
If it is not possible to implement interface at class B, you need to use reflection. See here (How to use reflection to call method by name) on how to call a method from a Type (so you will have to pass the type in constructor of A.
Upvotes: 2
Reputation: 6813
Yes, this is possible using the dynamic
keyword (in C# 4.0 or higher). Check the MSDN documentation for more info.
However, this leads to incredibly loose programming and can cause runtime issues that are difficult to debug. You're much better off creating an interface that class B will implement.
public class A
{
A(IDataReceiver instanceOfClassB)
{
//stuff...
}
public void SendProcessedString()
{
//some strings has been processd, I know that class B is going
//to have a public method like ReceiveData(string data){/*---*/}
instanceOfClassB.ReceiveData(data);
}
}
public B : Form, IDataReceiver
{
public void ReceiveData(string data)
{
textBox.Append(data + Environment.NewLine);
}
}
public interface IDataReceiver
{
void ReceiveData(string data);
}
Upvotes: 5