Chỉ chuyển một kiểu làm tham số trong C #


130

Theo giả thuyết, sẽ rất hữu ích cho tôi khi làm điều này:

foo.GetColumnValues(dm.mainColumn, int)
foo.GetColumnValues(dm.mainColumn, string)

trong đó phương thức GetColumns sẽ gọi một phương thức khác bên trong tùy thuộc vào kiểu được truyền vào.

Có, tôi có thể làm điều đó dưới dạng cờ boolean hoặc tương tự, tôi chỉ tự hỏi liệu có cách nào để vượt qua điều này không, và sau đó hỏi:

typeof (arg [1]) hoặc tương tự ...

Tôi cũng có thể ghi đè phương thức, sử dụng generic, v.v. - Tôi biết có nhiều cách khác nhau để thực hiện việc này, tôi chỉ tò mò liệu điều này có khả thi không.


Suy nghĩ của tôi chính xác, tùy thuộc vào foo thực sự là gì. foo.GetColumnValues<int>(dm.mainColumn)có thể là con đường để đi.
Sản xuất chính

1
Như tôi đã nói, tôi nhận ra có nhiều cách khác để làm điều này (cờ boolean, generics, ghi đè phương thức). Tôi chỉ tự hỏi liệu nó có thể là một tham số hay không.
Mark Mayo

@MarkMayo: Tôi không hiểu câu hỏi nếu bạn "biết rằng bạn cũng có thể ghi đè phương thức, sử dụng generic, v.v. và bạn biết rằng có nhiều cách khác nhau để làm điều này, bạn chỉ tò mò liệu điều này có khả thi không" . Vì vậy, bạn biết tất cả những điều này nhưng bạn tò mò liệu nó có thể không ??
Tim Schmelter

@TimSchmelter - ở dạng tôi mô tả. tức là truyền nó dưới dạng tham số thứ 2. Hóa ra, Reed đã nói những gì tôi đã theo đuổi - nơi bạn sử dụng (..., Loại gõ). Đó là những gì tôi đang tìm kiếm.
Mark Mayo

1
Câu hỏi hay, được ủng hộ, tôi thấy MS sử dụng Type làm tham số cho các toán tử cài sẵn trong VB.NET, ví dụ như trycast, và tôi thường ước mình có thể tự làm điều đó trong C # / VB - theo cách bạn mô tả.
Chalky

Câu trả lời:


213

Có hai cách tiếp cận phổ biến. Đầu tiên, bạn có thể vượt quaSystem.Type

object GetColumnValue(string columnName, Type type)
{
    // Here, you can check specific types, as needed:

    if (type == typeof(int)) { // ...

Điều này sẽ được gọi là: int val = (int)GetColumnValue(columnName, typeof(int));

Tùy chọn khác sẽ là sử dụng generic:

T GetColumnValue<T>(string columnName)
{
    // If you need the type, you can use typeof(T)...

Điều này có lợi ích là tránh được quyền anh và cung cấp một số loại an toàn, và sẽ được gọi là: int val = GetColumnValue<int>(columnName);


1
Bạn cũng có thể làm một phương pháp khuyến nông, public static T GetColumnValue <T> (string này ColumnName) {...} sau đó bạn có thể nói foo.GetColumnValues <string> (dm.mainColumn)
Joshua G

Nhưng làm thế nào để bạn xác định một phương thức có nhiều đối số và một trong số chúng phải là đối số chung? Vì giá trị chung được xác định trước danh sách đối số phương thức, làm cách nào để bạn biết cái nào nên là đối số chung?
Cầu

5
@BadmintonCat T Foo<T,U>(string arg1, U arg2)hoặc tương tự
Reed Copsey

Khi sử dụng cách tiếp cận đầu tiên, có cách nào để gán giá trị mặc định để nhập không? (ví dụ như một cái gì đó giống như object GetColumnValue(string columnName, Type type = object)? Điều đó không hoàn toàn dường như làm việc cho tôi, nhưng nó sẽ là hữu ích để biết.
Dave Cole

22

foo.GetColumnValues(dm.mainColumn, typeof(string))

Ngoài ra, bạn có thể sử dụng một phương pháp chung:

public void GetColumnValues<T>(object mainColumn)
{
    GetColumnValues(mainColumn, typeof(T));
}

và sau đó bạn có thể sử dụng nó như:

foo.GetColumnValues<string>(dm.mainColumn);

13

Bạn có thể chuyển một kiểu làm đối số, nhưng để làm như vậy bạn phải sử dụng typeof:

foo.GetColumnValues(dm.mainColumn, typeof(int))

Phương thức sẽ cần phải chấp nhận một tham số có kiểu Type.


trong đó phương thức GetColumns sẽ gọi một phương thức khác bên trong tùy thuộc vào kiểu được truyền vào.

Nếu bạn muốn hành vi này thì bạn không nên chuyển kiểu làm đối số mà thay vào đó hãy sử dụng tham số kiểu.

foo.GetColumnValues<int>(dm.mainColumn)

8
foo.GetColumnValues(dm.mainColumn, typeof(int));
foo.GetColumnValues(dm.mainColumn, typeof(string));

Hoặc sử dụng thuốc chung:

foo.GetColumnValues<int>(dm.mainColumn);
foo.GetColumnValues<string>(dm.mainColumn);

3
Tôi không dv bạn, nhưng nó có lẽ là bởi vì bạn đang hiển thị như thế nào nó sẽ được gọi và không nói rõ định nghĩa hàm
JConstantine

3
Tôi ghét nó khi mọi người cần đút thìa. Câu trả lời + một bản đọc ngắn gọn về MSDN là đủ. Tôi nghi ngờ rằng những người bỏ phiếu trả lời là những người trả lời cạnh tranh với nhau - thật nhỏ bé.
Danny Varod

1

Bạn có thể làm điều này, chỉ cần quấn nó vào typeof()

foo.GetColumnValues(typeof(int))

public void GetColumnValues(Type type)
{
    //logic
}

0

Bạn có thể sử dụng một đối số kiểu Type - iow, pass typeof (int). Bạn cũng có thể sử dụng generic để tiếp cận (có thể hiệu quả hơn).


0

Sử dụng các loại chung chung!

  class DataExtraction<T>
{
    DateRangeReport dateRange;
    List<Predicate> predicates;
    List<string> cids;

    public DataExtraction( DateRangeReport dateRange,
                           List<Predicate> predicates,
                           List<string> cids)            

    {
        this.dateRange = dateRange;
        this.predicates = predicates;
        this.cids = cids;
    }
}

Và gọi nó như thế này:

  DataExtraction<AdPerformanceRow> extractor = new DataExtraction<AdPerformanceRow>(dates, predicates , cids);
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.