This page collects ideas for loading JCas classes including customization(s).
Each UIMA type have feature structure instances represented by instances of a corresponding (usually generated) Java class.
- The instances of these classes are the feature structure; the fields store the feature values.
- Uima types which have natural corresponding Java equivalents have feature values stored using the natural corresponding Java types
- primitives: boolean, byte, short, int, long, float, double, String, \[arbitrary-java-objects] and arrays of these as xxx[].
- Uima types which have natural corresponding Java equivalents have feature values stored using the natural corresponding Java types
- Most UIMA built-in types have standard defined Java class definitions.
Design considerations
- Built-in types support - would be nice if these were not needlessly replicated
- 1 JVM, multiple type systems - most likely supported via a separate class loader for these
- This implies that the code which uses objects under the class loader be loaded from the same class loader; otherwise they can't "see" the loaded classes.
- A single type system may be used (via UIMA application APIs) for multiple different pipelines, and for multiple different sets of index definitions.
- Having a single type system for multiple different sets of index definitions is unlikely
- The index definition supplies the avoid-index-corruption information needed by the setters
- If supplied at JCas generation time, then the test can be inserted only where needed, rather than run time testing if it is needed for many types. Test is currently a Bitset lookup.
What's in a JCas cover class?
There are two classes for each type.
- x.y.z.Foo - each instance represents one Feature Structure; in v3 these can be GC'd
- x.y.z.Foo_Type - there is one instance per CAS (arbitrary view)
x.y.z.Foo
Has
- a field for each feature
- a reference to the _Type instance
- only for backwards compatibility for low-level access model
- Multiple instances per type system - one per CAS
- has ref to TypeImpl
- a reference to the CAS View (to support addToIndexes for the right view)
- a ref to a type-system-wide Bitset for index corruption testing
- Constructors
- new Foo(Cas)
- Methods
- getter / setter for all fields
- The setter methods may include index corruption checking code.
- May be code which tests at runtime on each set, whether or not this
- The setter methods may include index corruption checking code.
- indexed getter/setter for fields defined as arrays
- (via inheritance)
- a collection of get/set methods, one per boolean/byte/short.../double/String/TOP/JavaObject and arrays of these, kinds of values.
- The methods take an extra "offset" value, obtained from the Feature.
- Used for backwards compatibility with non-JCas styles, and for serialization and other "generic" operations
- a collection of get/set methods, one per boolean/byte/short.../double/String/TOP/JavaObject and arrays of these, kinds of values.
- getter / setter for all fields
x.y.z.Foo_Type
An instance is loaded when a new x.y.z.Foo(some-cas) is done, lazily.
has
- a ref to the TypeImpl
- a ref to the CAS (an arbitrary view, sometimes updated in v2), used for low level access patterns
Instances are accessed per CAS via
- a Map (kept per CAS) from the x.y.z.Foo Class to the corresponding x.y.z.Foo_type instance.
- The key is a x.y.z.Foo Class object, so instances loaded under different class loaders may have the same class name. This used to happen for PEARS (but not in v3).
- This happens when different generated x.y.z.Foo (due to different merged type systems) are running in the same JVM.
- This used to happen within one pipeline with PEAR switching, where the PEAR might have a different customization of a JCas class. In v3, that doesn't happen; all versions of a customization must be merged.
- If the Map has no entry,
- Load the _Type class itself, if not loaded (Map in TypeSystemImpl instance, key = name string, value = _Type Class).
- Make instance of it, populate map in CAS.svd.
- The key is a x.y.z.Foo Class object, so instances loaded under different class loaders may have the same class name. This used to happen for PEARS (but not in v3).