@Pure
SpecificationDeclares that a single method on a class is "Pure".
See the Wikipedia definition, from which the following is derived. Essentially:
Pure4J makes the distinction between implementation purity, and interface purity, as described below.
A pure implementation will:
Pure
.
Errors will be reported if a pure method accesses code not regarded to be implementation pure.@ImmutableValue
Specification)@Pure
will check that the method only accepts immutable parameters (see {@link ImmutableValue}).
This ensures that the pure methods are Thread Safe and means that, once invoked the state of their arguments cannot be changed while the
method is running. Otherwise, this would impact the determinism constraint. By adding the @Pure
annotation, you expect both interface and implementation purity to be observed in the method. Errors will be
reported if these constraints are not met.
You can disable purity checking (of both kinds) by adding the Enforcement
argument on this annotation.
You can disable the interface purity check by additionally adding the @PureParameters
annotation.
By setting the Enforcement
argument on this annotation you can either:
If you are writing code that uses generics, or implements an interface that takes arguments which are non-immutable values, you may need to test the interface purity at runtime.
You can do this by adding Pure4J.immutable(<args>)
as:
this
or super
call in a constructor.Pure4J.immutable
.ClassNotImmutableException
will be thrown for arguments that prove to be not immutableAlternatively, you can use the Pure4J.unsupported()
method to throw an UnsupportedOperationException
which will also disable parameter checking.
public String testParam2Good(Object in1, Object in2) { Pure4J.immutable(in1, in2); return in1.toString() + in2.toString(); }
Since @ImmutableValue
and @MutableUnshared
are class-level annotations, and specify the purity requirements for
instance methods only, one common use-case for the @Pure
annotation is in declaring static methods as being pure.
Use of reflection within your code can break these guarantees. The compile-time checker will make no attempt to ensure semantics where reflection is involved. (In fact, this is undecideable).
Lots of the methods in the Java language are pure, and can be used by your pure code. For example:
java.lang.Math
class.java.lang.StringBuilder
class. This is automatically used
by the Java compiler when concatenating strings.Pure code is free to construct @MutableUnshared
objects, or @ImmutableValue
objects,
since the constructors for both of these types of objects are registed pure.