3

我正在将 VB.Net 应用程序转换为 C#(以及学习 C#),但遇到了问题。其中一个函数接收一个对象,并根据传递的内容对某些参数进行修改。这样,一个函数可用于更新传递给它的任何控件,这在 VB 中运行良好。

完整的功能背后有更多的逻辑,但这里是一个缩小的版本,展示了基础知识:

public void TransformObject(object objObject, int LeftPadding, int TopPadding, int WidthChange, int HeightChange)
{        
    objObject.Top = TopPadding;
    objObject.Left = LeftPadding;
    objObject.Width = WidthChange;
    objObject.Height = HeightChange;
}

问题是没有定义'Top'、'Left'、'Width'、'Height'等,因为它使用的是对象类型。

有没有一种方法可以保留现有结构,而不必为每种可能的控件类型创建单独的函数或定义?

编辑:我正在使用 .Net 3.5 框架。

4

6 回答 6

1

您可以使用dynamic

public void TransformObject(object objObject, int LeftPadding, int TopPadding, int WidthChange, int HeightChange)
{        
    dynamic dynObject = (dynamic)objObject;
    dynObject.Top = TopPadding;
    dynObject.Left = LeftPadding;
    dynObject.Width = WidthChange;
    dynObject.Height = HeightChange;
}

Control或者找到所有这些类型共有的接口/基类(可能?),并在方法签名中使用它,而不是object.

于 2013-08-27T14:33:26.310 回答
1

使用基类,例如MyBaseClass具有TopLeftWidth和的定义Height

public class MyBaseClass
{
    public int Top {get; set;}
    public int Left{get; set;}
    public int Width {get; set;}
    public int Height {get; set;}

}

并且您要传入的每个类都应派生自该基类

public class MyDerivedClass : MyBaseClass
{
}
于 2013-08-27T14:33:30.280 回答
1

您将需要确定传递给函数的对象是否实现相同的接口或继承自公开这些属性的相同基类。如果他们这样做了,那么只需更改函数的接口,以便您接受通用接口/基类类型作为参数而不是object. 如果不是,那么您将面临令人讨厌的选择。

于 2013-08-27T14:35:07.053 回答
1

这里的解决方案之一是使用接口。例如,如果我理解你的问题,你可以试试这个:

public interface IMyInterface
    {
        int Top { get; set;}
        int Left { get; set; }
        int Width { get; set; }
        int Height { get; set; }
    }

public void TransformObject(object objObject, int LeftPadding, int TopPadding, int WidthChange, int HeightChange)
        {
            if (objObject is IMyInterface)
            {
                ((IMyInterface)objObject).Top = TopPadding;
                ((IMyInterface)objObject).Left = LeftPadding;
                ((IMyInterface)objObject).Width = WidthChange;
                ((IMyInterface)objObject).Height = HeightChange;
            }
        }

代码未优化,但这应该可以解决问题:)

于 2013-08-27T14:44:34.357 回答
1

我冒昧地猜测object被传递的实际上是一个Control(假设这是一个 WinForms 应用程序)。您可以更改方法签名以指定这一点并查看是否确实如此,或者您可以将对象强制转换为 aControl并彻底测试(和/或如果强制转换失败,则添加日志记录:

更改签名:

public void TransformObject(System.Windows.Forms.Control objObject, int LeftPadding, int TopPadding, int WidthChange, int HeightChange)
{        
    objObject.Top = TopPadding;
    objObject.Left = LeftPadding;
    objObject.Width = WidthChange;
    objObject.Height = HeightChange;
}

内部向下转型:

public void TransformObject(object objObject, int LeftPadding, int TopPadding, int WidthChange, int HeightChange)
{        
    var control = objObject as System.Windows.Forms.Control;
    if (control != null)
    {
        control.Top = TopPadding;
        control.Left = LeftPadding;
        control.Width = WidthChange;
        control.Height = HeightChange;
    }
    else 
    {
      // Turns out it isn't a control, throw an exception or Log it
    }  
}
于 2013-08-27T14:53:15.023 回答
-3

在调用方法之前不要定义对象的新实例。

object obj = new object()

TransformObject(obj,5,5,5,5)

public void TransformObject(object objObject, int LeftPadding, int TopPadding, int WidthChange, int HeightChange)
{        
    objObject.Top = TopPadding;
    objObject.Left = LeftPadding;
    objObject.Width = WidthChange;
    objObject.Height = HeightChange;
}
于 2013-08-27T14:35:10.083 回答