2016-04-22 9 views
2

Ist so etwas überhaupt möglich? Für eine Anwendung, die ich versuche zu machen, kann ein Benutzer mehrere (oder keine) E-Mails, Telefonnummern und Adressen für einen einzelnen Kontakt eingeben, aber auf der Vorderseite möchte ich nur die erste Telefonnummer anzeigen, E-Mail-Adresse und Adresse für jeden Kontakt (falls vorhanden).Wie wählt man nur eine Zeile aus allen Spalten aber die erste

Hier meine SQL-Abfrage ist, die Daten für die Beschaffung von (. Beachten Sie, dass es für die Lesbarkeit leicht modifiziert worden ist in der Praxis, ich bin für ein Cookie-SQL nicht abfragt.):

SELECT TC.FirstName + ' ' + TC.LastName AS FullName, TCE.EmailAddress, TCPN.PhoneNumber, TCA.[Address] + ", " + TCA.City + ', ' + TCA.[State] + ', ' + TCA.ZipCode AS FullAddress, TC.Notes 
FROM TContacts     AS TC 
INNER JOIN TContactEmails  AS TCE ON TCE.ContactID = TC.ContactID 
INNER JOIN TContactPhoneNumbers AS TCPN ON TCPN.ContactID = TC.ContactID 
INNER JOIN TContactAddresses AS TCA ON TCA.ContactID = TC.ContactID 
INNER JOIN TUserContacts  AS TUC ON TUC.ContactID = TC.ContactID 
INNER JOIN TUsers    AS TU ON TU.UserID = TUC.UserID 
WHERE TU.UserName = userCookie.Values["UserName"] 

Das gewünschte Ergebnis wäre etwas ähnliches zu verwenden SELECT TOP 1 statt nur SELECT, aber ich kann das nicht speziell tun, denn dann würde es nur den ersten Kontakt (FullName) anzeigen. Ich muss jeden Namen sehen, aber nicht jede FullAddress, PhoneNumber oder EmailAddress.

Die folgenden Informationen sind für, wenn es eine andere Lösung speziell für die SQL-Abfrage nicht gibt.

Diese SQL-Abfrage wird in einer Webseite verwendet, die ASP.NET und C# -Code verwendet und über ADO.NET-Befehle aufgerufen wird. Sobald die Abfrage aufgerufen wird, werden alle verwendeten Tabellen in ein DataAdapter-Objekt geladen und zum dynamischen Füllen einer ListView verwendet. Hier ist der Code für die (SQLstatement weggelassen, weil sie im wesentlichen oben aufgeführt wird):

 SqlConnection conn = new SqlConnection(WebConfigurationManager.ConnectionStrings["CPDM_NightingaleAConnectionString"].ConnectionString); 
     SqlCommand comm = new SqlCommand(sqlStatement, conn); 

     comm.CommandType = CommandType.Text; 
     comm.Connection = conn; 

     conn.Open(); 

     SqlDataAdapter dataAdapter = new SqlDataAdapter(comm); 
     DataSet ds = new DataSet(); 
     dataAdapter.Fill(ds, "TUsers, TUserContacts, TContactAddresses, TContactPhoneNumbers, TContactPhoneNumbers, TContactEmails, TContacts"); 
     lvContacts.DataSource = ds.Tables[0]; 
     lvContacts.DataBind(); 

     conn.Close(); 

Der ASP.NET-Code für das Listview erstellt dynamisch eine Tabelle basierend auf den Werten, etwa so:

<asp:ListView ID="lvContacts" runat="server"> 
     <ItemTemplate> 
      <tr> 
       <td><asp:LinkButton ID="LinkButton1" runat="server" Text='<%# Eval("FullName") %>' /></td> 
       <td><asp:LinkButton ID="LinkButton2" runat="server" Text='<%# Eval("EmailAddress") %>' /></td> 
       <td><asp:LinkButton ID="LinkButton3" runat="server" Text='<%# Eval("PhoneNumber") %>' /></td> 
       <td><asp:LinkButton ID="LinkButton4" runat="server" Text='<%# Eval("FullAddress") %>' /></td> 
       <td><asp:LinkButton ID="LinkButton5" runat="server" Text='<%# Eval("Notes") %>' /></td> 
      </tr>  
     </ItemTemplate> 
    </asp:ListView> 

Das ist bei weitem nicht die eleganteste Implementierung eines solchen Features, aber so wie es aussieht, bin ich kein Experte für die Tools, die ich verwende. Jede Hilfe zu diesem Thema würde sehr geschätzt werden.

Wenn jemand zufällig weiß, wie man einen Zeilenumbruch in der Mitte einer SQL SELECT-Anweisung hinzufügt, die bei der Konvertierung in HTML angezeigt wird, wäre das für die Organisation der FullAddress von großem Nutzen. CHAR(10) + CHAR(13) tat scheinbar nichts von Wert.

+0

Was den Zeilenumbruch betrifft, ist es möglicherweise besser, die Adresse in Ihrer SQL-Anweisung getrennt zu belassen und sie in Ihrem Link-Button-Code unter Verwendung von <% # Eval ("Adresse") + Umgebung aufzuteilen. NewLine + Eval ("Stadt") + "," + Eval ("State") + "" + Eval ("ZipCode")%> ' –

Antwort

4

Sie können ein verwenden Unterabfrage, die für diese Art von Abfragen in der Regel gut ist:

SELECT TC.FirstName + ' ' + TC.LastName AS FullName, 
(SELECT TOP 1 EmailAddress FROM TContactEmails WHERE ContactID = TC.ContactID) AS EmailAddress, 
(SELECT TOP 1 PhoneNumber FROM TContactPhoneNumbers WHERE ContactID = TC.ContactID) AS PhoneNumber, 
(SELECT TOP 1 [Address] + ", " + City + ', ' + [State] + ', ' + ZipCode FROM TContactAddresses WHERE ContactID = TC.ContactID) AS FullAddress, 
TC.Notes 
FROM TContacts     AS TC 
INNER JOIN TUserContacts  AS TUC ON TUC.ContactID = TC.ContactID 
INNER JOIN TUsers    AS TU ON TU.UserID = TUC.UserID 
WHERE TU.UserName = userCookie.Values["UserName"] 

Alternativ können Sie einen „Default“ boolean in der Tabelle und lassen Sie die Eingabe der Benutzer die Daten speichern ihre Standard-Adresse, Telefonnummer usw.

+1

Dies ist eine Antwort auch, aber wenn Sie eine große Menge an Datensätzen in TContac haben, äußere Anwendung viel besser als Unterabfrage. – FLICKER

+0

Ich habe die Leistung nicht analysiert, daher bin ich mir nicht sicher. Aber zumindest gaben wir ihm mehr als eine Option. :) –

+0

@BoydP Danke! Das funktioniert einwandfrei. Mein Programm ist ziemlich klein, deshalb wird Skalierung kein Problem sein, aber Flicker, danke auch für deine Antwort. Ich wusste bis jetzt noch nicht einmal, dass Cross-Joins existierten, und ich habe gesehen, dass dein Edit nach außen passt, also werde ich nachsehen, ob ich das später zur Arbeit bringen kann, aber im Moment passt das zu meinen Bedürfnissen. Danke euch beiden! – user3530169

1

Sie können die erste Telefonnummer für jeden Kontakt wählen mit Kreuz verbinden (nicht INNER JOIN) wie unten allgemeines Beispiel

select TC.*, pho.Phone, adr.[Address] 
from TContact AS TC 
    outer apply (select top 1 phone 
       from TContactPhoneNumbers 
       where ContactID = TC.ContactID) AS pho 
    outer apply (select top 1 [address] 
       from TContactAddresses 
       where ContactID = TC.ContactID) AS adr 
    outer apply (select top 1 [UserName] 
       from TUserContacts 
       where ContactID = TC.ContactID) AS uc 
    outer apply (select top 1 [UserName] 
       from TUsers 
       where UserId = uc.UserID) AS u 
where u.UserName = what ever ..... 

und anderen Tabellen hinzufügen, wie Sie sehen ...

+0

Das scheint genau das zu sein, wonach ich suche, aber wie funktioniert die Where-Klausel Arbeit? Ich versuche, 'WHERE TContactPhoneNumbers.ContactID = TContacts.ContactID' zu verwenden, aber ich erhalte immer einen" mehrteiligen Bezeichner TContacts.ContactID konnte nicht gebunden werden "Fehler. – user3530169

+0

Aliasing der Tabelle? Wenn Sie so vorgegangen sind, wie Flicker "TContacts as tc" vorgeschlagen hat, dann müssen Sie tc.ContactID, nicht TContacts.ContactID verwenden. –

+0

@BoydP Ich habe das zuerst versucht, beide TC.ContactID (mit der AS TC) und TContacts.ContactID (ohne die AS TC) führen zum gleichen Fehler. – user3530169

Verwandte Themen