简体   繁体   English

物业的动机是什么?

[英]What's the motivation for properties?

I'm a bit confused as to why languages have these. 我有点困惑为什么语言有这些。 I'm a Java programmer and at the start of my career so Java is the only language I've written in since I started to actually, you know, get it. 我是一名Java程序员,在我职业生涯的开始阶段,所以Java是我写的唯一一种语言,因为我开始实际上,你知道,得到它。

So in Java of course we don't have properties and we write getThis() and setThat(...) methods. 所以在Java中我们当然没有属性,我们编写了getThis()和setThat(...)方法。

What would we gain by having properties? 拥有房产我们会得到什么?

Thanks. 谢谢。

EDIT: another query: what naming conventions arise in languages with properties? 编辑:另一个问题:具有属性的语言中出现了哪些命名约定?

Which one looks more natural to you? 哪一个看起来更自然?

// A
person.setAge(25)
// B
person.age = 25;
// or
person.Age = 25; //depending on conventions, but that's beside the point

Most people will answer B. 大多数人会回答B.

It's not only syntaxic sugar, it also helps when doing reflection; 这不仅是语法糖,它在做反射时也有帮助; you can actually make the difference between data and operations without resorting to the name of the methods. 实际上,您可以在不依赖方法名称的情况下区分数据和操作。

Here is an example in C# for those not familiar with properties: 以下是C#中不熟悉属性的示例:

class Person
{
    public int Age
    {
        set
        {
            if(value<0)
                throw new ArgumentOutOfRangeException();

            OnChanged();
            age = value;
        }

        get { return age; }
    }

    private int age;
    protected virtual void OnChanged() { // ... }
}

Also, most people always use properties rather than promote a public member later for the same reason we always use get/set; 此外,大多数人总是使用属性而不是稍后推广公共成员,原因与我们总是使用get / set相同; there is no need to rewrite the old client code bound to data members. 没有必要重写绑定到数据成员的旧客户端代码。

The syntax is much nicer: 语法更好:

button.Location += delta;

than: 比:

button.setLocation(button.getLocation() + delta);

Edit: 编辑:

The code below assumes that you are doing everything by hand. 下面的代码假设您手动完成所有操作。 In my example world the compiler would generate the simple get/set methods and convert all direct variable access to those methods. 在我的示例世界中,编译器将生成简单的get / set方法并将所有直接变量访问转换为这些方法。 If that didn't then the client code would have to be recompiled which defeats a big part of the purpose. 如果没有,那么客户端代码将不得不重新编译,这将失去很大一部分目的。

Original: 原版的:

The main argument for properties is that it removes the need to recompile your code if you go from a variable to a method. 属性的主要参数是,如果从变量转换为方法,则无需重新编译代码。

For instance: 例如:

public class Foo
{
    public int bar;
}

If we later decided to validation to "bar" we would need to do this: 如果我们后来决定验证“bar”,我们需要这样做:

public class Foo
{
    private int bar;

    public void setBar(final int val)
    {
        if(val <= 0)
        {
            throw new IllegalArgumentException("val must be > 0, was: " + val);
        }

        bar = val;
    }

    public int getBar()
    {
        return (bar);
    }
}

But adding the set/get method would break all of the code. 但添加set / get方法会破坏所有代码。 If it was done via properties then you would be able to add the validation after the fact without breaking client code. 如果它是通过属性完成的,那么您可以在事后添加验证而不破坏客户端代码。

I personally don't like the idea - I am much happier with the idea of using annotation and having the simple set/get geterated automatically with the ability to profive your own set/get implementations as needed (but I don't like hidden method calls). 我个人不喜欢这个想法 - 我对使用注释的想法感到非常高兴,并且可以根据需要自动设置/获取简单的set / get geterated(但我不喜欢隐藏的方法)调用)。

Two reasons: 两个原因:

  1. Cleaned/terser syntax; Cleaned / terser语法; and
  2. It more clearly indicates to the user of the class the difference between state (properties) and behaviour (methods). 它更清楚地向类的用户指示状态(属性)和行为(方法)之间的差异。

In Java the getters and setters are in essence properties. 在Java中,getter和setter本质上是属性。

In other modern languages (c#) , etc it just makes the syntax easier to work with/comprehend. 在其他现代语言(c#)等中,它只是使语法更容易使用/理解。

They are unnecessary, and there are workarounds in most cases. 它们是不必要的,大多数情况下都有解决方法。

It's really a matter of preference, but if the language you're using supports them I would recommend using them :) 这真的是一个偏好的问题,但如果您使用的语言支持他们,我会建议使用它们:)

I struggled with this at first, too, however I've really come to appreciate them. 我一开始也很挣扎,但是我真的很欣赏他们。 The way I see it, properties allow me to interact with the exposed data in a natural way without losing the encapsulation provided by getter/setter methods. 我看到它的方式,属性允许我以自然的方式与暴露的数据交互,而不会失去getter / setter方法提供的封装。 In other words, I can treat my properties as fields but without really exposing the actual fields if I choose not to. 换句话说,我可以将我的属性视为字段,但如果我不选择,则不会真正暴露实际字段。 With automatic properties in C# 3.0 it gets even better as for most fields -- where I want to allow the consumer to read/write the data -- I have even less to write: 使用C#3.0中的自动属性,对于大多数字段来说它变得更好 - 我希望允许消费者读/写数据 - 我写的更少:

public string Prop { get; set; }

In the case where I want partial visibility, I can restrict just the accessor I want easily. 在我想要部分可见性的情况下,我可以轻松地限制我想要的访问者。

public string Prop { get; private set; }

All of this can be done with getter/setter methods, but the verbiage is much higher and the usage is much less natural. 所有这些都可以通过getter / setter方法完成,但是措辞要高得多,而且使用率也不那么自然。

A general rule of object oriented programming is that you never change an existing interface. 面向对象编程的一般规则是您永远不会更改现有接口。 This ensures that while in inner content may change for the objects calling the object don't need to know this. 这确保了在内部内容中可以改变调用对象的对象,而不需要知道这一点。

Properties in other languages are methods masquerading as a specific language feature. 其他语言中的属性是伪装成特定语言特征的方法。 In Java a property is distinguished only by convention. 在Java中,属性仅按惯例区分。 While in general this works, there are cases where it limits you. 虽然一般来说这是有效的,但有些情况会限制你。 For example sometimes you would to use hasSomething instead of isSomething of getSomething. 例如,有时您会使用hasSomething而不是isSomething of getSomething。

So it allows flexibility of names, while tools and other code depending on can still tell the difference. 因此它允许名称的灵活性,而工具和其他依赖的代码仍然可以区分。

Also the code can be more compact and the get and set are grouped together by design. 此外,代码可以更紧凑,并且get和set通过设计组合在一起。

In Object Oriented Software Construction 2 Bertrand Meyer calls this the "Uniform Access Principle" and the general idea is that when a property goes from a simple one (ie just an integer) to a derived one (a function call), the people using it shouldn't have to know. 面向对象的软件构造中,2 Bertrand Meyer称之为“统一访问原则”,一般的想法是当一个属性从一个简单的(即只是一个整数)变为派生的(一个函数调用)时,使用它的人不应该知道。

You don't want everyone using your code to have to change from 您不希望每个人都使用您的代码来改变

int x = foo.y; int x = foo.y;

to

int x = foo.y(); int x = foo.y();

That breaks encapsulation because you haven't changed your "interface" just your "implementation". 这破坏了封装,因为你没有改变你的“接口”只是你的“实现”。

You can also create derived fields and read-only/write-only fields. 您还可以创建派生字段和只读/只写字段。 Most Properties that I've seen in languages I've worked in allow you to not only assign simple fields, but also full functions to properties. 我在我所使用的语言中看到的大多数属性不仅允许您分配简单字段,还可以为属性分配完整功能。

Properties provide a simple method to abstract the details behind a set of logic in an object down to a single value to the outside world. 属性提供了一种简单的方法,可以将对象中一组逻辑背后的细节抽象为外部世界的单个值。

While your property may start out only as a value, this abstraction decouples the interface such that it's details can be changed later with minimal impact. 虽然您的属性可能仅作为值开始,但此抽象将接口分离,以便稍后可以在影响最小的情况下更改其详细信息。

A general rule of thumb is that abstraction and loose coupling are good things. 一般的经验法则是抽象和松散耦合是好事。 Properties are a pattern that achieve both. 属性是实现两者的模式。

Properties at the language level are a bad idea. 语言级别的属性是个坏主意。 There's no good convention for them and they hide performance deficits in the code. 对他们没有好的约定,他们隐藏了代码中的性能缺陷。

It's all about bindings 这都是关于绑定的

There was a time when I considered properties to just be syntactic sugar (ie help the developer by having them type a bit less). 曾经有一段时间我认为属性只是语法糖(即通过让它们输入更少的东西来帮助开发人员)。 As I've done more and more GUI development, and started using binding frameworks (JGoodies, JSR295), I have discovered that language level properties are much, much more than syntactic sugar. 随着我越来越多的GUI开发,并开始使用绑定框架(JGoodies,JSR295),我发现语言级属性远远超过语法糖。

In a binding scenario, you essentially define rules that say 'property X of object A should always be equal to property Y of object B'. 在绑定方案中,您基本上定义了规则,即“对象A的属性X应始终等于对象B的属性Y”。 Shorthand is: Ax <-> By 简写是:Ax < - > By

Now, imagine how you would go about actually writing a binding library in Java. 现在,想象一下如何在Java中实际编写绑定库。 Right now, it is absolutely not possible to refer to 'x' or 'y' directly as language primitives. 现在,绝对不可能直接将'x'或'y'称为语言原语。 You can only refer to them as strings (and access them via reflection). 您只能将它们称为字符串(并通过反射访问它们)。 In essence, A."x" <-> B."y" 本质上,A。“x”< - > B.“y”

This causes massive, massive problems when you go to refactor code. 当你去重构代码时,这会导致大量的大量问题。

There are additional considerations, including proper implementation of property change notifications. 还有其他注意事项,包括正确实施属性更改通知。 If you look at my code, every blessed setter requires a minimum of 3 lines to do something that is incredibly simple. 如果你看一下我的代码,每个受祝福的setter都需要至少3行来做一些非常简单的事情。 Plus one of those 3 lines includes yet another string: 加上这3行中的一行包含另一个字符串:

public void setFoo(Foo foo){
  Foo old = getFoo();
  this.foo = foo;
  changeSupport.firePropertyChange("foo", old, foo);
}

all of these strings floating around is a complete nightmare. 所有这些浮动的字符串都是一场彻头彻尾的噩梦。

Now, imagine if a property was a first class citizen in the language. 现在,想象一下房产是否是该语言的一等公民。 This starts to provide almost endless possibilities (for example, imagine registering a listener with a Property directly instead of having to muck with PropertyChangeSupport and it's 3 mystery methods that have to get added to every class). 这开始提供几乎无限的可能性(例如,想象一下直接用一个Property注册一个监听器而不必使用PropertyChangeSupport,并且它必须添加到每个类中的3个神秘方法)。 Imagine being able to pass the property itself (not the value of the property, but the Property object) into a binding framework. 想象一下,能够将属性本身(不是属性的值,而是Property对象)传递给绑定框架。

For web tier developers, imagine a web framework that can build it's own form id values from the names of the properties themselves (something like registerFormProperties(myObject.firstname, myObject.lastname, someOtherObject.amount) to allow for round-trip population of object property values when the form is submitted back to the server. Right now to do that, you'd have to pass strings in, and refactoring becomes a headache (refactoring actually becomes downright scary once you are relying on strings and reflection to wire things up). 对于Web层开发人员,想象一个Web框架,它可以从属性本身的名称(类似于registerFormProperties(myObject.firstname,myObject.lastname,someOtherObject.amount))构建它自己的表单id值,以允许对象的往返填充将表单提交回服务器时的属性值。现在要做到这一点,你必须传入字符串,并且重构变得令人头疼(一旦你依赖字符串和反射连接起来,重构实际上变得非常可怕)。

So anyway, For those of us who are dealing with dynamic data updates via binding, properties are a much needed feature in the language - way more than just syntactic sugar. 所以,无论如何,对于我们这些通过绑定处理动态数据更新的人来说,属性是语言中非常需要的功能 - 不仅仅是语法糖。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 默认方法与抽象类的接口,动机是什么? - Interface with default methods vs abstract class, and what's the motivation? RequireThis背后的动机是什么? - What is the motivation behind RequireThis? Tomcat 为每个 HTTP 请求分配一个新线程,那么使用 future.get() 的动机是什么? - Tomcat allocates a new thread per HTTP request so what's the motivation of using future.get()? 使用工厂方法模式而不是简单工厂的动机是什么 - What is the motivation of using factory method pattern rather than simple factory 在Java中,将所有接口提取到单独项目中的技术动机是什么? - In Java, what is the technical motivation for extracting all interfaces into a separate project? 使用非Sun JRE / JDK的动机是什么? - What is the motivation for using a non-Sun JRE/JDK? Properties.loadFromXML()和Properties.storeToXML()方法的目的是什么? - What's the purpose of Properties.loadFromXML() and Properties.storeToXML() methods? Microsoft JDBC中的JTDS属性等效于什么? - What's the equivalent of JTDS properties in Microsoft JDBC? JSR-310中两个不同的基于周的年定义的动机是什么? - What is the motivation for two different week-based-year definitions in JSR-310? 使用Maven的动机是什么? 我可以只创建一个构建脚本吗? - What is the motivation of using Maven? Can I just create a build script instead?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM