Om de grootte van de rij in tekstweergave te meten, kunt u de hele rij naar tekst casten, wat veel sneller is dan het aaneenschakelen van afzonderlijke kolommen:
SELECT length(profile::text) FROM profile;
Maar er zijn 3 (of 4) problemen met deze uitdrukking in een index:
-
De syntaxisafkorting
profile::text
wordt niet geaccepteerd inCREATE INDEX
, moet u extra haakjes of standaard toevoegen aan de standaardsyntaxiscast(profile AS text)
-
Nog steeds hetzelfde probleem dat @jjanes al besproken :alleen
IMMUTABLE
functies zijn toegestaan in indexexpressies en het casten van een rijtype naartext
voldoet niet aan deze eis. Je zou een nepIMMUTABLE
. kunnen bouwen wrapper-functie, zoals Jeff geschetst heeft. -
Er is een inherente ambiguïteit (dat geldt ook voor Jeff's antwoord!):als je een kolomnaam hebt die hetzelfde is als de tabelnaam (wat een veelvoorkomend geval is), kun je niet verwijzen naar het rijtype in
CREATE INDEX
aangezien de identifier altijd eerst wordt omgezet in de kolomnaam. -
Klein verschil met uw origineel:dit voegt kolomscheidingstekens, rij-decorators en mogelijk escape-tekens toe aan de
text
vertegenwoordiging. Zou niet veel uit moeten maken voor uw gebruik.
Echter , zou ik een radicaler alternatief willen voorstellen als ruwe indicator voor de grootte van een rij:pg_column_size()
. Nog korter en sneller en vermijdt problemen 1 , 3 en 4 :
SELECT pg_column_size(profile) FROM profile;
Nummer 2 blijft echter:pg_column_size()
is ook alleen STABLE
. U kunt een eenvoudige en goedkope SQL-wrapperfunctie maken:
CREATE OR REPLACE FUNCTION pg_column_size(profile)
RETURNS int LANGUAGE sql IMMUTABLE AS
'SELECT pg_catalog.pg_column_size($1)';
en ga dan verder zoals @jjanes geschetst. Meer details:
Merk op dat ik de functie heb gemaakt met het rijtype profile
als parameter. Postgres staat functieoverbelasting toe, daarom kunnen we dezelfde functienaam gebruiken. Als we nu het overeenkomende rijtype invoeren in pg_column_size()
onze aangepaste functie komt beter overeen volgens resolutie functietype regels en wordt gekozen in plaats van de polymorfe systeemfunctie. U kunt ook een aparte naam gebruiken en eventueel de functie ook polymorf maken ...
Gerelateerd: