2014-12-17 14:35 GMT-02:00 Jean Pereira <[email protected]>:
>
> CREATE TEMP table table_a (field_a time);
>
> Efetuo a inserção de um dado, sendo que utilizo o current_timestamp, e o
> banco efetua a conversão automática para time na hora que insere.
>
> insert into table_a values (current_timestamp);
>
> Mas se eu efetuo um simples select utilizando tambem o current_timestamp
>
> select * from table_a where field_a = current_timestamp;
>
>
Bem, existe uma diferença básica. Só para exemplificar o conceito, no
PostgreSQL as conversões de tipos são tratadas por funções, sendo que
existe três tipos de conversões:

- explícitas: são aquelas que você deixa claro, exemplo:
CAST(current_timestamp AS time) ou current_timestamp::time
- implícitas: (em inglês chamados de "implicit casts") são aqueles
literalmente implícitos, por exemplo a conversão de "int" para "bigint", um
"int" sempre cabe num "bigint", logo essa conversão pode ser feita sem
perda alguma, *SEMPRE*
- implícitas no assinalamento: (em inglês "assignment casts") são usadas em
operações de atribuição, por exemplo, num INSERT, num UPDATE ou ALTER TABLE
... ALTER ... TYPE (na verdade só conheço esses três, não sei se tem mais).

Sabendo disso fica fácil identificar o seu caso. No INSERT o PostgreSQL irá
procurar por um "implict cast" ou "assignment cast" de "timestamptz" para
"time", existindo (e existe) este será usado. Já no SELECT o PostgreSQL irá
procurar primeiro por um operador de igualdade entre os dois tipos em
questão, se este não existir (e não existe) aí sim ele irá procurar por um
"implicit cast", que no caso também não existe, logo o erro (não tenho
certeza se a ordem é essa operador depois cast, mas creio que seja).

Só pra deixar documentado, se for no psql e executar `\dC 'timestamp with
time zone'` irá obter:

    postgres=# \dC 'timestamp with time zone'
                                          List of casts
             Source type         |         Target type         |
Function   |   Implicit?

-----------------------------+-----------------------------+-------------+---------------
     abstime                     | timestamp with time zone    |
timestamptz | yes
     date                        | timestamp with time zone    |
timestamptz | yes
     timestamp without time zone | timestamp with time zone    |
timestamptz | yes
     timestamp with time zone    | abstime                     |
abstime     | in assignment
     timestamp with time zone    | date                        |
date        | in assignment
     timestamp with time zone    | timestamp without time zone |
timestamp   | in assignment
     timestamp with time zone    | timestamp with time zone    |
timestamptz | yes
     timestamp with time zone    | time without time zone      |
time        | in assignment
     timestamp with time zone    | time with time zone         |
timetz      | in assignment
    (9 rows)

A última linha é o "cast" que foi usado no seu comando INSERT. Resumindo,
os hackers do PostgreSQL acharam que seria razoável a conversão de
"timestamptz" para "time" de forma implícita, mas somente numa atribuição.

Espero que tenha esclarecido.

Atenciosamente,
-- 
Matheus de Oliveira
Analista de Banco de Dados
Dextra Sistemas - MPS.Br nível F!
www.dextra.com.br/postgres
_______________________________________________
pgbr-geral mailing list
[email protected]
https://listas.postgresql.org.br/cgi-bin/mailman/listinfo/pgbr-geral

Responder a