none
La funzione CONCAT in progetta vista RRS feed

  • Domanda

  • Ciao

    In SSMS tasto desto su Vista->Progetta ed inserisco il seguente codice:

    SELECT        dbo.tbNomiIndirizzi.Id, dbo.tbNomiIndirizzi.DataRegistrazione, dbo.tbNominativi.Nome,CONCAT(dbo.tbIndirizzi.Strada, ',  ', dbo.tbIndirizzi.Civico) AS Indirizzo, GETDATE() AS Data
    FROM            dbo.tbNominativi INNER JOIN
                             dbo.tbNomiIndirizzi ON dbo.tbNominativi.Id = dbo.tbNomiIndirizzi.IdNome INNER JOIN
                             dbo.tbIndirizzi ON dbo.tbNomiIndirizzi.IdIndirizzo = dbo.tbIndirizzi.Id LEFT OUTER JOIN
                             dbo.tbClienti ON dbo.tbNomiIndirizzi.Id = dbo.tbClienti.Id

    Se provo ad eseguirlo, l'editor lo modifica in:

    SELECT        dbo.tbNomiIndirizzi.Id, dbo.tbNomiIndirizzi.DataRegistrazione, dbo.tbNominativi.Nome, { fn CONCAT(dbo.tbIndirizzi.Strada, ',  ', dbo.tbIndirizzi.Civico) } AS Indirizzo, GETDATE() AS Data
    FROM            dbo.tbNominativi INNER JOIN
                             dbo.tbNomiIndirizzi ON dbo.tbNominativi.Id = dbo.tbNomiIndirizzi.IdNome INNER JOIN
                             dbo.tbIndirizzi ON dbo.tbNomiIndirizzi.IdIndirizzo = dbo.tbIndirizzi.Id LEFT OUTER JOIN
                             dbo.tbClienti ON dbo.tbNomiIndirizzi.Id = dbo.tbClienti.Id

    cioè modifica il campo dove ho insrito la funzione concat ed in più mi lancia un avviso di errore che dice:

    "La funzione CONCAT richiede 2 argomenti"

    il che non è vero.

    Grazie

    martedì 14 novembre 2017 08:27

Risposte

  • Ciao,

    Non mi è chiaro quale sia l'altra query senza case ? (Quella che usa il CONCAT canonico forse?)

    In ogni caso, per convincerti, prova a lanciare questo script e vedrai come la nullabilità di un campo, anche non stringa, non influisce sulla sua concatenazione in quanto, come scritto nella doc, viene automaticamente convertita a stringa vuota.

    CREATE TABLE Prova(
      
      Strada VARCHAR(10) NULL,
      Civico INT NULL
     );
      
      INSERT INTO Prova(Strada) VALUES ('Prova');
      
      SELECT CONCAT(Strada, ',', Civico)
      FROM Prova;

    A presto,

    Gabriele


    • Modificato Gabriele Etta martedì 14 novembre 2017 12:08
    • Contrassegnato come risposta Cracken66 martedì 14 novembre 2017 15:34
    martedì 14 novembre 2017 12:08

Tutte le risposte

  • Ciao,

    {fn CONCAT(stringa1, stringa2)} è la funzione canonica di concatenazione che accetta al più due argomenti introdotta automaticamente dal designer, mentre quella che utilizzi tu all'inizio accetta un numero non determinato di input. Quello che farei io è prendere lo script della view e lanciarlo normalmente senza passare dalla progettazione della vista. 

    Per maggiori informazioni: CONCAT()

    A presto,

    Gabriele






    martedì 14 novembre 2017 08:55
  • Quindi per creare viste che contegono la funzione concat devo necessariamente usare lo script.

    Comunque se uso, ad es., concat in una clausola case non da errori e non modifica nulla:

    CASE WHEN Civico IS NULL THEN Strada ELSE CONCAT(dbo.tbIndirizzi.Strada, ', ', dbo.tbIndirizzi.Civico) END AS Indirizzo

    Grazie

    martedì 14 novembre 2017 09:58
  • Il problema è il CONCAT canonico generato dallo script. Potresti muoverti così:

    - Crei la View dal designer sostituendo il CONCAT generato:

    { fn CONCAT(dbo.tbIndirizzi.Strada, ',  ', dbo.tbIndirizzi.Civico) } AS Indirizzo

    Con:

    CONCAT(dbo.tbIndirizzi.Strada, ',  ', dbo.tbIndirizzi.Civico) AS Indirizzo

    - Generi la view direttamente come script senza passare dal designer.

    Nell'esempio dell'ultima risposta quindi non è il CASE a far si che il CONCAT funzioni ma il fatto che tu stia utilizzando il CONCAT "standard" e non canonico che prende più di due argomenti. Questo lo noti anche dal modo con cui sono scritte le due versioni della stessa funzione.

    A presto,

    Gabriele

    martedì 14 novembre 2017 10:04
  • Nei due esempi ho utilizzato il CONCAT sempre con tre argomenti e funziona solo quello che usa il CASE.

    Usa questo codice in progetta vista e verrai che non darà errori:

    SELECT        dbo.tbNomiIndirizzi.Id, dbo.tbNomiIndirizzi.DataRegistrazione, dbo.tbNominativi.Nome, CASE WHEN civico IS NULL THEN strada ELSE CONCAT(dbo.tbIndirizzi.Strada, ',  ', dbo.tbIndirizzi.Civico) END AS Indirizzo, GETDATE() 
                             AS Data
    FROM            dbo.tbNominativi INNER JOIN
                             dbo.tbNomiIndirizzi ON dbo.tbNominativi.Id = dbo.tbNomiIndirizzi.IdNome INNER JOIN
                             dbo.tbIndirizzi ON dbo.tbNomiIndirizzi.IdIndirizzo = dbo.tbIndirizzi.Id LEFT OUTER JOIN
                             dbo.tbClienti ON dbo.tbNomiIndirizzi.Id = dbo.tbClienti.Id

    Ciao

    martedì 14 novembre 2017 11:07
  • Ciao,

    Non mi è chiaro quale sia l'altra query senza case ? (Quella che usa il CONCAT canonico forse?)

    In ogni caso, per convincerti, prova a lanciare questo script e vedrai come la nullabilità di un campo, anche non stringa, non influisce sulla sua concatenazione in quanto, come scritto nella doc, viene automaticamente convertita a stringa vuota.

    CREATE TABLE Prova(
      
      Strada VARCHAR(10) NULL,
      Civico INT NULL
     );
      
      INSERT INTO Prova(Strada) VALUES ('Prova');
      
      SELECT CONCAT(Strada, ',', Civico)
      FROM Prova;

    A presto,

    Gabriele


    • Modificato Gabriele Etta martedì 14 novembre 2017 12:08
    • Contrassegnato come risposta Cracken66 martedì 14 novembre 2017 15:34
    martedì 14 novembre 2017 12:08
  • Che con lo script funziona tutto regolarmente non mi devi convincere.

    E' con progettta vista che non va, cioè il CONCAT "canonico" lancia l'errore tranne se lo inserisco in un (io ho fatto un esempio) CASE.

    Grazie

    martedì 14 novembre 2017 14:15
  • Non ti voglio convincere sullo script in se, ma sul fatto che la query

    SELECT        dbo.tbNomiIndirizzi.Id, dbo.tbNomiIndirizzi.DataRegistrazione, dbo.tbNominativi.Nome, CASE WHEN civico IS NULL THEN strada ELSE CONCAT(dbo.tbIndirizzi.Strada, ',  ', dbo.tbIndirizzi.Civico) END AS Indirizzo, GETDATE() 
                             AS Data
    FROM            dbo.tbNominativi INNER JOIN
                             dbo.tbNomiIndirizzi ON dbo.tbNominativi.Id = dbo.tbNomiIndirizzi.IdNome INNER JOIN
                             dbo.tbIndirizzi ON dbo.tbNomiIndirizzi.IdIndirizzo = dbo.tbIndirizzi.Id LEFT OUTER JOIN
                             dbo.tbClienti ON dbo.tbNomiIndirizzi.Id = dbo.tbClienti.Id

    Utilizzi la classica CONCAT() che non ha nulla a che vedere con quella canonica:-) Il problema comunque mi pare si sia risolto eseguendolo non da designer da come dici tu.

    Gabriele



    martedì 14 novembre 2017 14:19
  • Era per dire che quello che hai scritto l'ho verificato e funziona, mentre se desidero utilizzarla (la funzione CONCAT) in progetta vista, la devo contenere ad es., in un costrutto CASE.

    Si, quella "canonica".

    Ciao e grazie.

    martedì 14 novembre 2017 15:33