WCF服务和对象构造函数

本文关键字:构造函数 对象 服务 WCF | 更新日期: 2023-09-27 18:05:32

我正在学习WCF服务。我有一个方法返回一个我创建的名为gpposition的对象。GPS Position对象有一个纬度和一个经度。如果没有这些属性,对象就不应该真正存在。我想让构造函数接受Lat和Long浮点数。因此,当创建对象时,值是设置的,并且永远不会无效(Unset)。

但是,它是我的WCF服务的对象。作为WCF服务对象,我的调用应用程序使用,可以有一个构造函数?如果我在调用代码中使用var position = new GpsPosition{ lat=1, lon=1 };,构造函数会工作吗?你能在WCF类中有构造函数吗?

我认为它们在不同的语言之间是共享的——所以如果服务被Java使用,例如,我不确定构造函数将如何触发。对象结构被共享给调用的应用程序,不是吗?你能在构造函数中调用。net代码吗(在这种情况下,还有getter和setter方法)?

如果构造函数不可用-是否有一种方法来确保我的对象永远无效?(必须在-180和+180之间有有效的后期/长值)?

WCF服务和对象构造函数

答案取决于您的类型GpsPosition使用的序列化模型。WCF中最常用的两个对象是POCO(普通的旧CLR对象)和[DataContract]。在前者中,对象必须有一个无参数的构造函数,这违背了您的要求(需要设置一次值)。在后者中,不调用对象构造函数,而是创建该类型的未初始化实例,并通过反序列化设置其成员。

所以构造函数不是验证来自网络的对象的替代方法。验证对象而不是构造函数所需要的是序列化回调,它在反序列化完成时被调用。WCF序列化器将在反序列化完成时调用它们,在那里您可以检查对象是否被正确初始化,否则抛出异常。这篇博文有关于序列化回调的更多细节,下面的代码显示了您的场景的一个可能实现。

[DataContract]
public class GpsPosition
{
    private float _lat;
    private float _lon;
    private bool _latWasSet;
    private bool _lonWasSet;
    public GpsPosition(float lat, float lon)
    {
        _lat = lat;
        _lon = lon;
    }
    [DataMember]
    public float lat
    {
        get { return _lat; }
        private set
        {
            _lat = value;
            _latWasSet = true;
        }
    }
    [DataMember]
    public float lon
    {
        get { return _lon; }
        private set
        {
            _lon = value;
            _lonWasSet = true;
        }
    }
    [OnDeserialized]
    void OnDeserialized(StreamingContext ctx)
    {
        if (!_latWasSet || _!lonWasSet ||
            _lat < -90 || _lat > 90 ||
            _lon < -180 || _lon > 180)
        {
            throw new InvalidOperationException("Required property is missing");
        }
    }
}