2009-12-31 6 views
1

Редактировать: В реальной жизни у меня нет класса Book. Это просто пример, который должен быть ясен. Реальная проблема действительно нуждается в размышлении, чтобы ее решить.Динамический вызов метода класса

Предположим, что у меня есть несколько классов:

книги, Apple, двери.

class Book 
{ 
    ... 
    public decimal getPrice() 
    {...} 
    public string getTitle() 
    {...} 
    public decimal getAuthor() 
    {...} 
} 

и что-то подобное для других классов.

Может ли я вызвать метод класса динамически из строки:

Book myBook = new Book("Title", "Author", 44); 

string title = runMethod(myBook, "getTitle"); 
+1

Могу ли я спросить, как это будет использоваться? – Omar

+0

Да, пожалуйста. Я чувствую, что в этом вопросе я чего-то не хватает. – jac

+1

Вам не нужна рефрекция? Я использовал его в Java и рад, что C# тоже. и это долгая история, где его использовать. но это действительно необходимо. Пример, приведенный выше, является лишь примером для объяснения. Конечно, я не буду так использовать. – JCasso

ответ

3

Вы можете использовать что-то вроде этого, с помощью отражения:

class Program 
{ 
static void Main(string[] args) 
{ 
    var b = new Book("Book Title", 2342); 

    Console.WriteLine(CallMethod(b, "GetTitle", "Not Found")); 
} 

public static K CallMethod<T,K>(T a, string method, K defaultOjb) 
{ 
    var t = a.GetType(); 

    var mi = t.GetMethod(method); 
    if (mi == null) return defaultOjb; 

    var ret=mi.Invoke(a, new object[] {}); 

    return (K) ret; 
} 
} 

public class Book 
{ 
private readonly string _title; 
private readonly decimal _price; 

public decimal GetPrice() 
{ 
    return _price; 
} 
public string GetTitle() 
{ 
    return _title; 
} 

public Book(string title, decimal price) 
{ 
    _title = title; 
    _price = price; 
} 
} 
+0

Мой первый ответ 2010 года! – TheVillageIdiot

+0

Я принимаю его, и все ваши ответы в 2010 году будут приняты: P (Спасибо, это очень помогло) – JCasso

1

Уточняющего отражения и MethodInfo. Я считаю, что это приведет вас к тому пути, который вы ищете.

5

Вы можете сделать это через Reflection.

Book myBook = new Book("Title", "Author", 44); 

string title = (string) myBook.GetType().GetMethod("getTitle").Invoke(myBook, null); 
+0

Это довольно kluggy способ получить что-то обратно. – Chris

+2

В этом случае это совершенно глупо.Однако времена, когда отражение очень полезно, - и это, по крайней мере, демонстрирует требуемые типы и методы. –

0

Можно с отражением, но в данном примере, было бы проще просто вызвать метод непосредственно:

string title = myBook.getTitle(); 
+0

Очень верно, но я привел пример, чтобы быть понятным. – JCasso

+0

Вот что я бы предложил. – Chris

1

Предыдущие ответы верны при упоминании отражения.

Однако, если ваш истинный вопрос не сильно отличается от вашего примера, это не нужно.

Судя по вашему примеру, вы могли бы просто назвать это непосредственно:

string title = mybook.getTitle(); 

Если точка является то, что вы не знаете и не хотите, чтобы все равно, что конкретный объект вы быть дано вам может либо используйте базовый класс или интерфейс.

public interface IProduct 
{ 
    string Name { get; } 
    string Type { get; } 
    float Price { get; } 
} 

сделать ваши классы реализуют IProduct и вы гарантированы, что ваши классы будут реализованы свойства или функцию вы необходимыми, и что они будут общественности независимо от того, что вы имеете дело с «Книгой», «Яблоко», или «Дверь».

public void OutputProductsToConsole(List<IProduct> products) 
    { 
     for (int i = 0; i < products.Count; i++) 
     { 
      Console.WriteLine(products[i].Name + ": " + products[i].Price); 
     } 
    } 
+0

Нет, это не относится к моему вопросу. Извините, я знаю, какой интерфейс. Мне действительно нужно вызвать метод из строки. – JCasso

0

Вы создаете новый класс Book со значениями свойств. Не назначаете ли вы значения, чтобы их можно было вернуть позже?

public class Book 
{ 

    private string _title; 
    private decimal _price; 
    private string _author; 

    public Book(string title, decimal price, string author); 
    { 
     _title = title; 
     _price = price; 
     _author = author; 
    } 

    public string Title 
    { 
     get 
     { 
      return _title; 
     } 
    } 

    public decimal Price 
    { 
     get 
     { 
      return _price; 
     } 
    } 

    public string Author 
    { 
     get 
     { 
      return _author; 
     } 
    } 

} 

Еще лучше, если эти методы являются общими для всех ваших классов, создают интерфейс и наследуют его в ваших классах.

Смежные вопросы