The wildcards listed below are supported in many different places when specifying strings (e.g. file names).
'*' - zero or more characters '+' - one or more characters '?' - exactly one character '%' - exactly one character (backward compatible with FLAM4 and conform with ISPF (not in URLs)) '#' - exactly one digit (not supported on MVS, because '#' could be part of a qualifier) '=' - exactly one digit (supported on all platforms but mainly for MVS) '^' - escape character (put it before a wildcard character if it is part of the file/member name)
If one of the wildcard characters is part of the string itself, you
can escape the wildcard character with the caret (^).
'dat^*.txt' - the file "dat*.txt"
Wildcards are a powerful tool for file processing and searching in our compressed and encrypted archives.
Beside file names, wildcards can be used in the match records of a filter (MATCH.DATASET) to search inside an archive. A column of an archive is stored in a neutral internal form which is not text for every type, so the comparison is defined against a fixed string form of the column value.
STRING the text itself
DATE ISO-8601, YYYY-MM-DD[THH:MM:SS[.ffffff]][Z]
INTEGER, INT64 decimal, shortest form, no '+' on positive numbers,
'-' on negative numbers, no leading zeros
FLOAT decimal, shortest form, '.' as decimal point,
no '+', no thousands separator -- independent of the
machine's locale, so a pattern is portable
BINARY hexadecimal (base 16), UPPER CASE letters
How the pattern itself is written depends on the type, because a match record is read through the row specification like any other data.
STRING the text, as declared for the column
DATE in the layout declared for the column, transformed
field by field into the ISO form
FLOAT in the notation declared for the column, the decimal
separator translated and a group separator dropped
INTEGER, INT64 decimal digits and '-'; a column declared with another
BASE cannot be matched with wildcards, because a
pattern cannot be converted between bases
BINARY hexadecimal in either case, folded to upper case;
only ENCODE=BASE16 supports wildcards, since with
ENCODE=OFF the bytes of the pattern are the bytes of
the value, and BASE32 or BASE64 are out of scope
Not every wildcard is available for every type. Only a STRING column carries a code page (CCSID), so only there can the characters '#' and the escape '^' be recognised reliably: both are variant characters in EBCDIC and differ per code page. For all other types the supported set is
'*' '+' '?' '%' '='
which are part of the invariant EBCDIC character set and therefore mean the same on every platform. Using '#' or '^' on such a column is reported as an unsupported character together with its position. Nothing is lost by this: '#' and '=' both stand for exactly one digit, so write '=' instead. Escaping is not needed either, because none of the five characters can occur in the canonical string form of a number, a date or a hexadecimal value.
A pattern for a FLOAT column is written in the notation declared for that column, not in the comparison form. The declared decimal separator is translated and a declared group separator is dropped, so with SEPARATOR=COMMA the pattern '100=,0=' searches exactly what '100=.0=' would search on a column declared with a period. A separator that is neither the declared decimal nor the declared group separator is rejected.
Take care when the declared decimal separator is a comma and the match records are read as CSV: by default the comma is the field separator of the record as well. Either enclose the field, or take the comma out of the separator set. Both are set on the CSV format of the column, SEPCHR for the separator characters and FLDCHR for the enclosing ones.
col(name='PRICE' format.csv(sepchr=SEMICOLON) type.float(...))
The same applies to a date pattern whose declared separator is a comma, and to any other pattern that contains one.
A match record for a date column is written in the layout declared for that column, not in ISO. The pattern is transformed field by field into the ISO form before it is compared.
YYYYMMDD + '2023==02' -> '2023-==-02' YYYY-MM-DD + '2023-*-15' -> '2023-*-15' DD.MM.YYYY + '==.02.2023' -> '2023-02-==' YY-MM-DD + '23-*-15' -> '2023-*-15' (century from PIVOT)
The two wildcard classes behave differently inside a field. '?', '%' and '=' stand for exactly one character, so they keep the width of the field and may be mixed with digits: '0=' for MM selects the months 01 to 09. '*' and '+' have an unknown length, so they are only accepted as a stand-in for a complete field. Writing them inside a field, for example '1*' for MM, is rejected because the field boundary would be ambiguous.
Two cases cannot be expressed at all and are rejected with a message.
wildcard in YY the century is derived via PIVOT, so the ISO year
would be ambiguous -- declare the column with YYYY
wildcard in DDD the Julian day of year has no counterpart in the
ISO form YYYY-MM-DD
A wildcard that reaches the indexed part of a column makes the index (signature) unusable for that column, so the column always matches on index level and the decision is left to the comparison. The result is the same either way, only the search is slower. Whether this is silent, a warning or an error is controlled by SIGNWC.
For STRING and DATE the position of a wildcard decides: the index stays usable as long as the wildcard is outside the indexed part. With an index over the ISO year for example, '2023-*-15' can still use it while '*-02-15' cannot.
For INTEGER, INT64, FLOAT and BINARY a wildcard always removes the column from the index. The internal form of a number has a variable length and no position of its own for a single digit, so there is no part of it over which a signature could still be computed.