Benutzer mit den meisten Antworten
Suche nach SQL-Statement

Frage
-
Bin auf der Suche nach einem SQL-Statement.
Grundlage:
Visual Studio Express 2013 für Windows Desktop
ACCDB-Datenbank (eingebunden über Datenquelle)Ich habe zwei Tabellen:
Tabelle1 mit Prüfungsfragen (jeder Datensatz hat einen eindeutigen IDX)
Tabelle2 mit Prüfungsantworten je Teilnehmen (die zugehörige Frage wird als Prüfungsfragen-IDX eingetragen)Frage:
Ich suche ein SQL-Statement (arbeite zur Zeit mit dem Abfrage-Editor), welches mir eine Liste der noch nicht beantworteten Fragen (aus Tabelle1) je Teilnehmer ausgibt.Danke vorab
Ronald
Antworten
-
Hallo Ronald,
wenn Du alle bekommen willst, d. h. auch die Teilnehmer die noch gar nichts beantwortet haben, müsstest Du über drei Tabellen gehen. Siehe unten stehenden Beispiel - mit SQL Server erstellt, die Abfrage (ohne CROSS JOIN) sollte auch mit Access 20xx funktionieren:
CREATE TABLE Fragen ( FrageID int NOT NULL CONSTRAINT PK_Fragen PRIMARY KEY, Frage nvarchar(100) NOT NULL); CREATE TABLE Teilnehmer ( TeilnehmerID int NOT NULL CONSTRAINT PK_TeilnehmerID PRIMARY KEY, Name nvarchar(50) NOT NULL); CREATE TABLE Antworten ( AntwortenID int IDENTITY(1, 1) NOT NULL PRIMARY KEY, TeilnehmerID int NOT NULL, FrageID int NOT NULL, Antwort int NOT NULL, CONSTRAINT UK_Antworten UNIQUE (TeilnehmerID, FrageID)); GO INSERT INTO Fragen (FrageID, Frage) VALUES (1, N'Frage 1'), (2, N'Frage 2'), (3, N'Frage 3'); INSERT INTO Teilnehmer (TeilnehmerID, Name) VALUES (1001, N'Teilnehmer 1'), (1002, N'Teilnehmer 2'), (1003, N'Teilnehmer 3'), (1004, N'Teilnehmer 4'); INSERT INTO Antworten (TeilnehmerID, FrageID, Antwort) VALUES (1001, 1, 1), (1001, 2, 2), (1001, 3, 3), (1002, 2, 1), (1002, 3, 3), (1003, 1, 1); GO SELECT * FROM Teilnehmer, Fragen WHERE NOT EXISTS(SELECT * FROM Antworten WHERE Teilnehmer.TeilnehmerID = Antworten.TeilnehmerID AND Fragen.FrageID = Antworten.FrageID) ORDER BY Teilnehmer.TeilnehmerID, Fragen.FrageID; -- oder (ANSI 92 CROSS JOIN) SELECT * FROM Teilnehmer CROSS JOIN Fragen WHERE NOT EXISTS(SELECT * FROM Antworten WHERE Teilnehmer.TeilnehmerID = Antworten.TeilnehmerID AND Fragen.FrageID = Antworten.FrageID) ORDER BY Teilnehmer.TeilnehmerID, Fragen.FrageID; GO DROP TABLE Fragen, Teilnehmer, Antworten; GO
(oben hat Teilnehmer 4 keine Antwort gegeben, 1 alle, 2 und 3 teile)
Gruß Elmar
- Als Antwort markiert Dimitar DenkovMicrosoft contingent staff, Administrator Donnerstag, 8. Januar 2015 07:19
-
Hallo Ronald,
generell ist es immer hilfreich, wenn Du sowohl die exakte Tabellenstruktur (wenn machbar, als CREATE TABLE Statements) sowie einige Beispieldatensätze (als INSERT INTO Statement) und das gewünschte Ergebnis postest.
Um deine Frage zu beantworten, fehlt eigentlich aber eh noch die Teilnehmertabelle. Ich nehme an, diese existiert und ist in Tabelle2 mit den jeweiligen ID Werten verknüpft).
In dem Fall würde ich es mal so probieren:
SELECT f.ID AS IDFrage, a.ID AS IDAntwort, t.ID AS IDTeilnehmer FROM Fragen f LEFT JOIN Antworten a ON a.IDFrage = f.ID RIGHT JOIN Teilnehmer t ON a.IDTeilnehmer = t.ID WHERE a.IDFrage IS NULL
Ob das bei dir nun überhaupt so machbar wäre, weiß ich nicht, da ich die Tabellenstrukutur nicht kenne. Poste daher bitte die fehlenden (o.g.) Informationen, dann kann ich das Beispiel ergänzen und/oder korrigieren.
Gruß, Stefan
Microsoft MVP - Visual Developer ASP/ASP.NET
http://www.asp-solutions.de/ - Consulting, Development
http://www.aspnetzone.de/ - ASP.NET Zone, die ASP.NET Community- Als Antwort markiert Dimitar DenkovMicrosoft contingent staff, Administrator Donnerstag, 8. Januar 2015 07:19
-
Danke für alle Antworten
Ich habe es allerdings anders gelöst.
Habe mir eine DataGridView erstellt. Im ersten Durchlauf habe ich alle Fragen aus der Datenbank eingetragen. Im Zweiten Durchlauf habe ich in einer neuen Spalte - basierend auf einer SQL-Abfrage - eingetragen, ob der Kunde die Frage schon beantwortet hat. Diese Lösung hat für mich den Vorteil, dass ich mir zusätzliche Spalten mit Detailinformationen, Berechnungen und optische Hinweise einbauen konnte.
Per CellClick kann ich mir jetzt zudem gezielt die Frage bzw deren Antwort ansehen.
Danke für eure Bemühungen
Ronald- Als Antwort markiert Dimitar DenkovMicrosoft contingent staff, Administrator Donnerstag, 8. Januar 2015 07:19
Alle Antworten
-
Hallo Ronald,
wenn Du alle bekommen willst, d. h. auch die Teilnehmer die noch gar nichts beantwortet haben, müsstest Du über drei Tabellen gehen. Siehe unten stehenden Beispiel - mit SQL Server erstellt, die Abfrage (ohne CROSS JOIN) sollte auch mit Access 20xx funktionieren:
CREATE TABLE Fragen ( FrageID int NOT NULL CONSTRAINT PK_Fragen PRIMARY KEY, Frage nvarchar(100) NOT NULL); CREATE TABLE Teilnehmer ( TeilnehmerID int NOT NULL CONSTRAINT PK_TeilnehmerID PRIMARY KEY, Name nvarchar(50) NOT NULL); CREATE TABLE Antworten ( AntwortenID int IDENTITY(1, 1) NOT NULL PRIMARY KEY, TeilnehmerID int NOT NULL, FrageID int NOT NULL, Antwort int NOT NULL, CONSTRAINT UK_Antworten UNIQUE (TeilnehmerID, FrageID)); GO INSERT INTO Fragen (FrageID, Frage) VALUES (1, N'Frage 1'), (2, N'Frage 2'), (3, N'Frage 3'); INSERT INTO Teilnehmer (TeilnehmerID, Name) VALUES (1001, N'Teilnehmer 1'), (1002, N'Teilnehmer 2'), (1003, N'Teilnehmer 3'), (1004, N'Teilnehmer 4'); INSERT INTO Antworten (TeilnehmerID, FrageID, Antwort) VALUES (1001, 1, 1), (1001, 2, 2), (1001, 3, 3), (1002, 2, 1), (1002, 3, 3), (1003, 1, 1); GO SELECT * FROM Teilnehmer, Fragen WHERE NOT EXISTS(SELECT * FROM Antworten WHERE Teilnehmer.TeilnehmerID = Antworten.TeilnehmerID AND Fragen.FrageID = Antworten.FrageID) ORDER BY Teilnehmer.TeilnehmerID, Fragen.FrageID; -- oder (ANSI 92 CROSS JOIN) SELECT * FROM Teilnehmer CROSS JOIN Fragen WHERE NOT EXISTS(SELECT * FROM Antworten WHERE Teilnehmer.TeilnehmerID = Antworten.TeilnehmerID AND Fragen.FrageID = Antworten.FrageID) ORDER BY Teilnehmer.TeilnehmerID, Fragen.FrageID; GO DROP TABLE Fragen, Teilnehmer, Antworten; GO
(oben hat Teilnehmer 4 keine Antwort gegeben, 1 alle, 2 und 3 teile)
Gruß Elmar
- Als Antwort markiert Dimitar DenkovMicrosoft contingent staff, Administrator Donnerstag, 8. Januar 2015 07:19
-
Hallo Ronald,
generell ist es immer hilfreich, wenn Du sowohl die exakte Tabellenstruktur (wenn machbar, als CREATE TABLE Statements) sowie einige Beispieldatensätze (als INSERT INTO Statement) und das gewünschte Ergebnis postest.
Um deine Frage zu beantworten, fehlt eigentlich aber eh noch die Teilnehmertabelle. Ich nehme an, diese existiert und ist in Tabelle2 mit den jeweiligen ID Werten verknüpft).
In dem Fall würde ich es mal so probieren:
SELECT f.ID AS IDFrage, a.ID AS IDAntwort, t.ID AS IDTeilnehmer FROM Fragen f LEFT JOIN Antworten a ON a.IDFrage = f.ID RIGHT JOIN Teilnehmer t ON a.IDTeilnehmer = t.ID WHERE a.IDFrage IS NULL
Ob das bei dir nun überhaupt so machbar wäre, weiß ich nicht, da ich die Tabellenstrukutur nicht kenne. Poste daher bitte die fehlenden (o.g.) Informationen, dann kann ich das Beispiel ergänzen und/oder korrigieren.
Gruß, Stefan
Microsoft MVP - Visual Developer ASP/ASP.NET
http://www.asp-solutions.de/ - Consulting, Development
http://www.aspnetzone.de/ - ASP.NET Zone, die ASP.NET Community- Als Antwort markiert Dimitar DenkovMicrosoft contingent staff, Administrator Donnerstag, 8. Januar 2015 07:19
-
Hallo Stefan
Anbei die Informationen wie gewünscht.
Tabelle1 (Antworten):
ID (IDX), ID_Kunde, ID_Skill, ErgebnisTabelle2 (Fragen):
ID (IDX), Frage, BeschreibungJede Frage kann 1:n Antworten haben.
Ich will lediglich die unbeantworteten Fragen je Kunden wissen.
Danke vorab
Ronald
-
Hi Ronald,
um zu wissen, welcher Kunde nicht vollständig geantwortet hat, benötigst Du für den Fall, dass ein Kunde keine Antwort abgegeben hat, eine Kundenliste (mit ID_Kunde). Es sind noch weitere Bedingungen erforderlich, z.B., ob jeder Kunde zu einer Frage nur eine oder mehrere Antworten abgegeben kann. Zur Übersichtlichkeit sollte die Fremdschlüsselspalte der Tabelle1 nicht auch ID genannt werden, da mit ID eigentlich ein eindeutiger Identifikator eines Datensatzes in der Tabelle angenommen wird, der für das Aktualisieren von Daten benötigt wird. Besser wäre als Benennung der Fremdschlüsselspalte ID_Frage.Wenn Du die Liste mit den Kunden hast und nur eine Antwort je Frage von einem Kunden zulässig ist, kannst Du mit Gruppierung je ID_Kunde und Count alle Kunden anzeigen lassen, bei denen die gefundene Anzahl nicht der Anzahl der Fragen entspricht. -> s. auch Elmars Beispiel.
--
Peter- Als Antwort vorgeschlagen Peter Fleischer Sonntag, 28. Dezember 2014 12:52
- Nicht als Antwort vorgeschlagen Peter Fleischer Sonntag, 28. Dezember 2014 12:52
- Bearbeitet Peter Fleischer Sonntag, 28. Dezember 2014 12:52
-
Danke für alle Antworten
Ich habe es allerdings anders gelöst.
Habe mir eine DataGridView erstellt. Im ersten Durchlauf habe ich alle Fragen aus der Datenbank eingetragen. Im Zweiten Durchlauf habe ich in einer neuen Spalte - basierend auf einer SQL-Abfrage - eingetragen, ob der Kunde die Frage schon beantwortet hat. Diese Lösung hat für mich den Vorteil, dass ich mir zusätzliche Spalten mit Detailinformationen, Berechnungen und optische Hinweise einbauen konnte.
Per CellClick kann ich mir jetzt zudem gezielt die Frage bzw deren Antwort ansehen.
Danke für eure Bemühungen
Ronald- Als Antwort markiert Dimitar DenkovMicrosoft contingent staff, Administrator Donnerstag, 8. Januar 2015 07:19