define, and then provide one in the second
operator's definition. Since <productname>PostgreSQL</productname>
knows that commutative operators come in pairs, when it sees the
second definition it will automatically go back and fill in the
missing <literal>COMMUTATOR</literal> clause in the first
definition.
</para>
</listitem>
<listitem>
<para>
Another, more straightforward way is just to
include <literal>COMMUTATOR</literal> clauses in both definitions.
When <productname>PostgreSQL</productname> processes the first
definition and realizes that <literal>COMMUTATOR</literal> refers to
a nonexistent operator, the system will make a dummy entry for that
operator in the system catalog. This dummy entry will have valid
data only for the operator name, left and right operand types, and
owner, since that's all that <productname>PostgreSQL</productname>
can deduce at this point. The first operator's catalog entry will
link to this dummy entry. Later, when you define the second
operator, the system updates the dummy entry with the additional
information from the second definition. If you try to use the dummy
operator before it's been filled in, you'll just get an error
message.
</para>
</listitem>
<listitem>
<para>
Alternatively, both operators can be defined
without <literal>COMMUTATOR</literal> clauses
and then <command>ALTER OPERATOR</command> can be used to set their
commutator links. It's sufficient to <command>ALTER</command>
either one of the pair.
</para>
</listitem>
</itemizedlist>
In all three cases, you must own both operators in order to mark
them as commutators.
</para>
<para>
Pairs of negator operators can be defined using the same methods
as for commutator pairs.
</para>
<para>
It is not possible to specify an operator's lexical precedence in
<command>CREATE OPERATOR</command>, because the parser's precedence behavior
is hard-wired. See <xref linkend="sql-precedence"/> for precedence details.
</para>
<para>
The obsolete options <literal>SORT1</literal>, <literal>SORT2</literal>,
<literal>LTCMP</literal>, and <literal>GTCMP</literal> were formerly used to
specify the names of sort operators associated with a merge-joinable
operator. This is no longer necessary, since information about
associated operators is found by looking at B-tree operator families
instead. If one of these options is given, it is ignored except
for implicitly setting <literal>MERGES</literal> true.
</para>
<para>
Use <link linkend="sql-dropoperator"><command>DROP OPERATOR</command></link> to delete user-defined operators
from a database. Use <link linkend="sql-alteroperator"><command>ALTER OPERATOR</command></link> to modify operators in a
database.
</para>
</refsect1>
<refsect1>
<title>Examples</title>
<para>
The following command defines a new operator, area-equality, for
the data type <type>box</type>:
<programlisting>
CREATE OPERATOR === (
LEFTARG = box,
RIGHTARG = box,
FUNCTION = area_equal_function,
COMMUTATOR = ===,
NEGATOR = !==,
RESTRICT = area_restriction_function,
JOIN = area_join_function,
HASHES, MERGES
);
</programlisting></para>
</refsect1>
<refsect1>
<title>Compatibility</title>
<para>
<command>CREATE OPERATOR</command> is a
<productname>PostgreSQL</productname> extension. There are no
provisions for user-defined operators in the SQL standard.
</para>
</refsect1>
<refsect1>
<title>See Also</title>
<simplelist type="inline">
<member><xref linkend="sql-alteroperator"/></member>
<member><xref linkend="sql-createopclass"/></member>
<member><xref linkend="sql-dropoperator"/></member>
</simplelist>
</refsect1>
</refentry>