Path: blob/master/src/java.desktop/share/classes/java/beans/Expression.java
41152 views
/*1* Copyright (c) 2000, 2013, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation. Oracle designates this7* particular file as subject to the "Classpath" exception as provided8* by Oracle in the LICENSE file that accompanied this code.9*10* This code is distributed in the hope that it will be useful, but WITHOUT11* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or12* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License13* version 2 for more details (a copy is included in the LICENSE file that14* accompanied this code).15*16* You should have received a copy of the GNU General Public License version17* 2 along with this work; if not, write to the Free Software Foundation,18* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.19*20* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA21* or visit www.oracle.com if you need additional information or have any22* questions.23*/2425package java.beans;2627/**28* An {@code Expression} object represents a primitive expression29* in which a single method is applied to a target and a set of30* arguments to return a result - as in {@code "a.getFoo()"}.31* <p>32* In addition to the properties of the super class, the33* {@code Expression} object provides a <em>value</em> which34* is the object returned when this expression is evaluated.35* The return value is typically not provided by the caller and36* is instead computed by dynamically finding the method and invoking37* it when the first call to {@code getValue} is made.38*39* @see #getValue40* @see #setValue41*42* @since 1.443*44* @author Philip Milne45*/46public class Expression extends Statement {4748private static Object unbound = new Object();4950private Object value = unbound;5152/**53* Creates a new {@link Expression} object54* for the specified target object to invoke the method55* specified by the name and by the array of arguments.56* <p>57* The {@code target} and the {@code methodName} values should not be {@code null}.58* Otherwise an attempt to execute this {@code Expression}59* will result in a {@code NullPointerException}.60* If the {@code arguments} value is {@code null},61* an empty array is used as the value of the {@code arguments} property.62*63* @param target the target object of this expression64* @param methodName the name of the method to invoke on the specified target65* @param arguments the array of arguments to invoke the specified method66*67* @see #getValue68*/69@ConstructorProperties({"target", "methodName", "arguments"})70public Expression(Object target, String methodName, Object[] arguments) {71super(target, methodName, arguments);72}7374/**75* Creates a new {@link Expression} object with the specified value76* for the specified target object to invoke the method77* specified by the name and by the array of arguments.78* The {@code value} value is used as the value of the {@code value} property,79* so the {@link #getValue} method will return it80* without executing this {@code Expression}.81* <p>82* The {@code target} and the {@code methodName} values should not be {@code null}.83* Otherwise an attempt to execute this {@code Expression}84* will result in a {@code NullPointerException}.85* If the {@code arguments} value is {@code null},86* an empty array is used as the value of the {@code arguments} property.87*88* @param value the value of this expression89* @param target the target object of this expression90* @param methodName the name of the method to invoke on the specified target91* @param arguments the array of arguments to invoke the specified method92*93* @see #setValue94*/95public Expression(Object value, Object target, String methodName, Object[] arguments) {96this(target, methodName, arguments);97setValue(value);98}99100/**101* {@inheritDoc}102* <p>103* If the invoked method completes normally,104* the value it returns is copied in the {@code value} property.105* Note that the {@code value} property is set to {@code null},106* if the return type of the underlying method is {@code void}.107*108* @throws NullPointerException if the value of the {@code target} or109* {@code methodName} property is {@code null}110* @throws NoSuchMethodException if a matching method is not found111* @throws SecurityException if a security manager exists and112* it denies the method invocation113* @throws Exception that is thrown by the invoked method114*115* @see java.lang.reflect.Method116* @since 1.7117*/118@Override119public void execute() throws Exception {120setValue(invoke());121}122123/**124* If the value property of this instance is not already set,125* this method dynamically finds the method with the specified126* methodName on this target with these arguments and calls it.127* The result of the method invocation is first copied128* into the value property of this expression and then returned129* as the result of {@code getValue}. If the value property130* was already set, either by a call to {@code setValue}131* or a previous call to {@code getValue} then the value132* property is returned without either looking up or calling the method.133* <p>134* The value property of an {@code Expression} is set to135* a unique private (non-{@code null}) value by default and136* this value is used as an internal indication that the method137* has not yet been called. A return value of {@code null}138* replaces this default value in the same way that any other value139* would, ensuring that expressions are never evaluated more than once.140* <p>141* See the {@code execute} method for details on how142* methods are chosen using the dynamic types of the target143* and arguments.144*145* @see Statement#execute146* @see #setValue147*148* @return The result of applying this method to these arguments.149* @throws Exception if the method with the specified methodName150* throws an exception151*/152public Object getValue() throws Exception {153if (value == unbound) {154setValue(invoke());155}156return value;157}158159/**160* Sets the value of this expression to {@code value}.161* This value will be returned by the getValue method162* without calling the method associated with this163* expression.164*165* @param value The value of this expression.166*167* @see #getValue168*/169public void setValue(Object value) {170this.value = value;171}172173/*pp*/ String instanceName(Object instance) {174return instance == unbound ? "<unbound>" : super.instanceName(instance);175}176177/**178* Prints the value of this expression using a Java-style syntax.179*/180public String toString() {181return instanceName(value) + "=" + super.toString();182}183}184185186