+ private static final long serialVersionUID = -4787195606494761540L;
+
+ NodeIdentifierWithPredicates(final QName node) {
+ super(node);
+ }
+
+ public static @NonNull NodeIdentifierWithPredicates of(final QName node) {
+ return new Regular(node, ImmutableMap.of());
+ }
+
+ public static @NonNull NodeIdentifierWithPredicates of(final QName node, final QName key, final Object value) {
+ return new Singleton(node, key, value);
+ }
+
+ public static @NonNull NodeIdentifierWithPredicates of(final QName node, final Entry<QName, Object> entry) {
+ return of(node, entry.getKey(), entry.getValue());
+ }
+
+ public static @NonNull NodeIdentifierWithPredicates of(final QName node, final Map<QName, Object> keyValues) {
+ return keyValues.size() == 1 ? of(keyValues, node)
+ // Retains ImmutableMap for empty maps. For larger sizes uses a shared key set.
+ : new Regular(node, ImmutableOffsetMap.unorderedCopyOf(keyValues));
+ }
+
+ public static @NonNull NodeIdentifierWithPredicates of(final QName node,
+ final ImmutableOffsetMap<QName, Object> keyValues) {
+ return keyValues.size() == 1 ? of(keyValues, node) : new Regular(node, keyValues);
+ }
+
+ @Deprecated
+ public static @NonNull NodeIdentifierWithPredicates of(final QName node,
+ final SharedSingletonMap<QName, Object> keyValues) {
+ return of(node, keyValues.getEntry());
+ }
+
+ private static @NonNull NodeIdentifierWithPredicates of(final Map<QName, Object> keyValues, final QName node) {
+ return of(node, keyValues.entrySet().iterator().next());
+ }
+
+ /**
+ * Return the set of predicates keys and values. Keys are guaranteeed to be unique.
+ *
+ * @return Predicate set.
+ */
+ @Beta
+ public abstract @NonNull Set<Entry<QName, Object>> entrySet();
+
+ /**
+ * Return the predicate key in the iteration order of {@link #entrySet()}.
+ *
+ * @return Predicate values.
+ */
+ @Beta
+ public abstract @NonNull Set<QName> keySet();
+
+ /**
+ * Return the predicate values in the iteration order of {@link #entrySet()}.
+ *
+ * @return Predicate values.
+ */
+ @Beta
+ public abstract @NonNull Collection<Object> values();
+
+ @Beta
+ public final @Nullable Object getValue(final QName key) {
+ return keyValue(requireNonNull(key));
+ }
+
+ @Beta
+ public final <T> @Nullable T getValue(final QName key, final Class<T> valueClass) {
+ return valueClass.cast(getValue(key));