Alt 20.01.2012, 19:01:14   #1 (permalink)
schwankend^^

ID: 215354
Lose-Remote
Reallife

Reg: 22.05.2006
Beiträge: 1.505
Gsus ist einfach richtig nettGsus ist einfach richtig nettGsus ist einfach richtig nettGsus ist einfach richtig nett
Standard Query mit 1:n-Relation

Hallo,

und schon wieder stehe ich vor einem kleinen Problem.

Ich programmiere gerade ein kleines Backup-System für den Eigengebrauch und habe dort nun folgende Datenbankstruktur erstellt:

Tabelle 1: global_backups
Hier sind allgemeine Informationen zu den Backups enthalten
backup_iddatetime...
12012-01-20 12:15:23...
22012-01-19 15:24:26...

Tabelle 2: global_backups_kinds
Hier sind die Backup-Arten zu den Backups gespeichert (MySQL oder FTP)
backup_idkind
1mysql
2mysql
2ftp

Tabelle 3: global_backups_projects
Hier sind die Projekte gespeichert die in den einzelnen Backups gespeichert sind
backup_idproject_name
1Projekt 1
2Projekt 1
2Projekt 2

Aus diesen Tabellen brauche ich nun ein Array, das wie folgt aussieht:
PHP-Code:
1:
2:
3:
4:
5:
6:
7:
array("backup_id" => [ID],
       
"datetime" => [datetime],
       
"kind" => array([=> ftp],
                            [
=> mysql]),
       
"projects" => array([=> "Projekt 1"],
                                 [
=> "Projekt 2"])

Da ich hierfür per MySQL leider keine direkte Lösung gefunden habe, baue ich mir dieses nun per PHP zusammen:

PHP-Code:
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
13:
$result $mysql->query("SELECT `backup_id`, DATE_FORMAT(`datetime`, '%%d.%%m.%%Y %%H:%%i:%%s') AS `datetime`, `kind`, `project_name` FROM `global_backups` LEFT JOIN `global_backups_kinds` USING(`backup_id`) LEFT JOIN `global_backups_projects` USING (`backup_id`) WHERE `project_name` ORDER BY `datetime` DESC");
while(
$row mysql_fetch_assoc($result)) {
    if(!isset(
$backups[$row['backup_id']])) {
        
$row['color'] = ($i%2==0)?"dark":"light";
        
$row['kind'] = array($row['kind']);
        
$row['project_name'] = array($row['project_name']);
        
$backups[$row['backup_id']] = $row;
        
$i++;
    } else {
        if(!
in_array($row['kind'], $backups[$row['backup_id']]['kind'])) $backups[$row['backup_id']]['kind'][] = $row['kind'];
        if(!
in_array($row['project_name'], $backups[$row['backup_id']]['project_name'])) $backups[$row['backup_id']]['project_name'][] = $row['project_name'];
    }

Soweit so gut, nun führt diese Vorgehensweise allerdings zu einigen Problemen:

Problem 1:
Eine Blätterfunktion um die Einträge auf mehrere Seiten zu verteilen ist mit MySQL und LIMIT x, y nun nicht mehr möglich, da ich nicht weiß, welche Datenreihen zusammengehören, bevor ich das PHP-Script drüberlaufen gelassen habe. Ich müsste also generell alle Backups auslesen und dann mit PHP auf die verschiedenen Seiten verteilen.

Problem 2:
Eine Suchfunktion, die nach einzelnen Projekten sucht und dennoch alle in diesen Backups enthaltene Projekte ausgibt ist nun auch nicht mehr möglich, denn wenn ich eine WHERE `project_name` IN (...) einfüge, erhalte ich ja logischerweise auch im Result nur die Daten, nach denen ich gesucht habe und nicht mehr die anderen Daten. für eine derartige Suchfunktion müsste ich also auch wieder alle Daten auslesen und dann mit PHP diese Daten durchsuchen.

In der Hoffnung, nicht bereits alle mit dem ganzen Text abgeschreckt zu haben: Gibt es hierfür vielleicht eine intelligentere Lösung mit MySQL?

Vielen Dank im Vorraus.

mfg
Gsus
Gsus ist offline   Mit Zitat antworten
Gesponsorte Links
Alt 21.01.2012, 00:46:46   #2 (permalink)
Multitalent
Benutzerbild von joschilein

ID: 9301
Lose-Remote

joschilein eine Nachricht über ICQ schicken
Reg: 05.05.2006
Beiträge: 1.414
joschilein genießt hohes Ansehenjoschilein genießt hohes Ansehenjoschilein genießt hohes Ansehenjoschilein genießt hohes Ansehenjoschilein genießt hohes Ansehenjoschilein genießt hohes Ansehenjoschilein genießt hohes Ansehenjoschilein genießt hohes Ansehenjoschilein genießt hohes Ansehenjoschilein genießt hohes Ansehenjoschilein genießt hohes Ansehen
Standard

Ich verstehe ehrlich gesagt deine Tabellenstruktur nicht so ganz. Was sollen denn z.B. diese Projektnamen aussagen? Wäre es nicht möglich wenigstens die Tabellen 2 und 3 in einer zu verschmelzen?

Und vielleicht ging es sogar mit einer Tabelle. Es könnte schließlich auch mehrere Backups geben. Zwei könnten den letztlich selben Zeitpunkt haben aber verschiedene Typen beinhalten.

Vermutlich wird das schon irgendwie ohne PHP-Umweg gehen, aber du müsstest eben mal erklären was der Zweck sein soll.


Heute schon gepixelt
joschilein ist offline   Mit Zitat antworten
Alt 21.01.2012, 08:33:19   #3 (permalink)
bekämpft die Mächte des Bösen
Benutzerbild von theHacker

ID: 69505
Lose-Remote

theHacker eine Nachricht über ICQ schicken theHacker eine Nachricht über AIM schicken theHacker eine Nachricht über MSN schicken theHacker eine Nachricht über Yahoo! schicken theHacker eine Nachricht über Skype™ schicken
Reg: 20.04.2006
Beiträge: 20.468
theHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes Ansehen
Standard

So von Tabellennamen- und Inhalten würd ich von 2x n:m-Beziehung ausgehen. Also dass Kinds und ProjectNames sowas wie Tags für ein Backup sind. Falls ja, wären hier erstmal zwei neue zusätzliche Tabellen angebracht, um n:m ordentlich zu mappen.
theHacker ist offline   Mit Zitat antworten
Alt 21.01.2012, 11:04:30   #4 (permalink)
schwankend^^

ID: 215354
Lose-Remote
Reallife

Reg: 22.05.2006
Beiträge: 1.505
Gsus ist einfach richtig nettGsus ist einfach richtig nettGsus ist einfach richtig nettGsus ist einfach richtig nett
Standard

mhh eigentlich sind es zwei 1:n beziehungen

und zwar: ein backup kann mehrere (unbegrenzt viele) Projekte beinhalten. und ein backup kann auch ein oder zwei arten (kinds) nämlich ftp, mysql oder eben beides beinhalten.

dabei ist dann eben in der backups-Tabelle die ID der PK, und in den anderen 2 jeweils die Kombination aus ID und zweitem feld.

Das ganze soll dann den Sinn haben, dass man sowohl Backups von nur einem Projekt und einer Art (z.B. nur MySQL-backup eines Projektes) machen kann, oder auch von dem ganzen Server (alle Projekte, MySQL+FTP).
Gsus ist offline Threadstarter   Mit Zitat antworten
Alt 21.01.2012, 11:11:01   #5 (permalink)
bekämpft die Mächte des Bösen
Benutzerbild von theHacker

ID: 69505
Lose-Remote

theHacker eine Nachricht über ICQ schicken theHacker eine Nachricht über AIM schicken theHacker eine Nachricht über MSN schicken theHacker eine Nachricht über Yahoo! schicken theHacker eine Nachricht über Skype™ schicken
Reg: 20.04.2006
Beiträge: 20.468
theHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes Ansehen
Standard

Zitat:
Zitat von Gsus Beitrag anzeigen
mhh eigentlich sind es zwei 1:n beziehungen

und zwar: ein backup kann mehrere (unbegrenzt viele) Projekte beinhalten.
Und nachdem ein Projekt einmal gebackupt wurde, kann es dann nie mehr gebackupt werden (1:n) oder möchtest du vielleicht noch ein zweites, drittes, ... Mal sichern (n:m)?

Zitat:
Zitat von Gsus Beitrag anzeigen
und ein backup kann auch ein oder zwei arten (kinds) nämlich ftp, mysql oder eben beides beinhalten.
Da diese 2 fix sind, sind das zwei Bool-Attribute am Backup, also keine extra Tabelle. In MySQL kannst du das mit einem SET in einer einzigen Spalte abbilden.
Deiner Formulierung nach ist es nämlich nicht möglich, in einem Backup Projekt A nur MySQL und Projekt B mit MySQL+FTP zu sichern.
theHacker ist offline   Mit Zitat antworten
Alt 21.01.2012, 11:32:01   #6 (permalink)
schwankend^^

ID: 215354
Lose-Remote
Reallife

Reg: 22.05.2006
Beiträge: 1.505
Gsus ist einfach richtig nettGsus ist einfach richtig nettGsus ist einfach richtig nettGsus ist einfach richtig nett
Standard

Zitat:
Zitat von theHacker Beitrag anzeigen
Und nachdem ein Projekt einmal gebackupt wurde, kann es dann nie mehr gebackupt werden (1:n) oder möchtest du vielleicht noch ein zweites, drittes, ... Mal sichern (n:m)?
naja schon: 1 Backup : n Projekte, nicht n Backups : m Projekte
Darum liegt der PK auch auf der Kombination von Backup-Id und Projektname. Dadurch kann ja ein Projektname in beliebig vielen Backups vorkommen.
Zitat:
Zitat von theHacker Beitrag anzeigen
Da diese 2 fix sind, sind das zwei Bool-Attribute am Backup, also keine extra Tabelle. In MySQL kannst du das mit einem SET in einer einzigen Spalte abbilden.
Deiner Formulierung nach ist es nämlich nicht möglich, in einem Backup Projekt A nur MySQL und Projekt B mit MySQL+FTP zu sichern.
darüber habe ich auch nachgedacht, allerdings habe ich dann ja auch einige unnötige Werte abgespeichert. Eigentlich möchte ich nämlich nur abspeichern, welche Werte wahr sind und nicht auchnoch welche unwahr sind, denn das kann ich ja einfach aus dem wahren ableiten.

mfg
Gsus
Gsus ist offline Threadstarter   Mit Zitat antworten
Alt 21.01.2012, 13:05:47   #7 (permalink)
Erfahrener Benutzer

ID: 129556
Lose-Remote

Reg: 28.02.2010
Beiträge: 439
tobomator tobomator tobomator tobomator tobomator tobomator
Standard

ich würde mal die Abfrage erweitern... (anders machen)
Also die Backup_ID ist ein PK?
Und wenn inden Tabellen jeweils der PK den gleichen Namen besitzt, so versteh ich das hier jedenfalls, dann kann man auch nen einfachen JOIN machen mittels ",".
Nun meine Variante mittels normalem JOIN (table1,table2,table3) : WHERE (tablename.Backup_ID = tablename2.Backup_ID AND tablename.Backup_ID = tablename3.Backup_ID)

Ich weißleider nicht mehr wo der unterschied zwischem dem inner join, left join, right outer join oder so liegt, aber bisher habe ich alles mit einem normalen join lösen können, wenn die Struktur der tabellen drunter mindestens die 3.NF erfüllt
tobomator ist offline   Mit Zitat antworten
Alt 21.01.2012, 14:27:10   #8 (permalink)
bekämpft die Mächte des Bösen
Benutzerbild von theHacker

ID: 69505
Lose-Remote

theHacker eine Nachricht über ICQ schicken theHacker eine Nachricht über AIM schicken theHacker eine Nachricht über MSN schicken theHacker eine Nachricht über Yahoo! schicken theHacker eine Nachricht über Skype™ schicken
Reg: 20.04.2006
Beiträge: 20.468
theHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes Ansehen
Standard

Zitat:
Zitat von Gsus Beitrag anzeigen
Darum liegt der PK auch auf der Kombination von Backup-Id und Projektname. Dadurch kann ja ein Projektname in beliebig vielen Backups vorkommen.
Hä? Versteh ich ned.
Backupst du Projekte oder Projektnamen? Ich mach immer Sicherungen von den Projekten. Der Name wird ja durch das Projekt vorgegeben, den muss ich also nicht sichern

Primary Key auf ID+Projektname is Quark. Eine ID-Spalte is implizit immer eine UID, also die is nie an ein anderes Datum geknüpft (außer an einen Foreign Key bei n:m).

Ich käme also auf:
  • Project (ProjectID, Name)
  • Backup (BackupID, Kind, DateTime)
  • BackupProject (ProjectID, BackupID)
Zitat:
Zitat von Gsus Beitrag anzeigen
darüber habe ich auch nachgedacht, allerdings habe ich dann ja auch einige unnötige Werte abgespeichert.
Nochmal: Hä?
Wo werden unnötige Werte abgespeichert?

edit:
Solltest du so einen Fall doch noch konstruieren wollen, wie ich in Post #5 im unteren Absatz geschildert hab, könntest du Kind von Backup in BackupProject schieben.
theHacker ist offline   Mit Zitat antworten
Alt 21.01.2012, 15:36:26   #9 (permalink)
schwankend^^

ID: 215354
Lose-Remote
Reallife

Reg: 22.05.2006
Beiträge: 1.505
Gsus ist einfach richtig nettGsus ist einfach richtig nettGsus ist einfach richtig nettGsus ist einfach richtig nett
Standard

Okay, offensichtlich habe ich mich falsch ausgedrückt Ich versuche es noch einmal.

Meine aktuellen Tabellen:
backups(backup_id, datum,...)
backups_kind(backup_id, kind{mysql, ftp})
backups_projects(backup_id, project_name)

eine Projekte-Tabelle habe ich ebenfalls:
projects(project_name,...)

Darüber hinaus habe ich die nötigen foreign keys (die sich hier durch die Namensgebung der Tabellenspalten denke ich selbst erklären) vergeben und auf CASCADE gestellt.

Dadurch ist mein project_name sozusagen eine project_id (nur eben in anderen datenformat)!

Es ist möglich, dass:
a) ein Backup nur FTP, oder nur MySQL oder beides
b) ein Backup mehr als ein Projekt umfässt

Es ist nicht möglich, dass:
a) ein Backup für Projekt 1 nur FTP und für Projekt 2 nur MySQL-Daten enthält (auch nicht in anderen Kombinationen)

Daher kommt meine Struktur deiner doch schon sehr dicht, nur dass ich kind ebenfalls ausgelagert habe. Ich denke nun habe ich auch verstanden, was du mit deinen zwei bool Attributen meintest. Du meintest ein extra Feld ("kind") in der Bakup-Tabelle wo nun eine 0 (=nur FTP), 1 (=nur MySQL) oder 2(=FTP+MySQL) drinsteht? Habe ich das so richtig verstanden?

Ich verstand folgendes:
Zwei extra boolean spalten ("mysql" + "ftp") in denen dann jeweils eine 0 oder 1 drinsteht. dadurch habe ich unnötige Informationen gespeichert (nämlich ich speichere, was nicht in Backup enthalten ist, wenn ich eine 0 in der Tabelle habe. Diese Daten kann ich mir aber ableiten, wenn ich nur speichere, was da schon enthalten ist, denn alles andere ist bekanntlich nicht enthalten).

Mit diesem Ansatz, könnte ich die Tabellenanzahl aber in der Tat um 1 verringern. Das löst nur leider immernoch nicht das eigentliche Problem Vielleicht hast du dazu auch noch eine Idee?

mfg
Gsus
Gsus ist offline Threadstarter   Mit Zitat antworten
Alt 21.01.2012, 16:40:10   #10 (permalink)
bekämpft die Mächte des Bösen
Benutzerbild von theHacker

ID: 69505
Lose-Remote

theHacker eine Nachricht über ICQ schicken theHacker eine Nachricht über AIM schicken theHacker eine Nachricht über MSN schicken theHacker eine Nachricht über Yahoo! schicken theHacker eine Nachricht über Skype™ schicken
Reg: 20.04.2006
Beiträge: 20.468
theHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes Ansehen
Standard

Zitat:
Zitat von Gsus Beitrag anzeigen
Dadurch ist mein project_name sozusagen eine project_id (nur eben in anderen datenformat)!
Böse, reine Speicherplatzverschwendung, aber wenn du garantieren kannst, dass ein Projekt niemals seinen Namen ändert, vo DB-Design her ok.
Zitat:
Zitat von Gsus Beitrag anzeigen
Es ist nicht möglich, dass: [...]
Ok, verstanden. Dann bleibt dieses Attribut also an der Sicherung, nicht am n:m-Glied.
Zitat:
Zitat von Gsus Beitrag anzeigen
Du meintest ein extra Feld ("kind") in der Bakup-Tabelle wo nun eine 0 (=nur FTP), 1 (=nur MySQL) oder 2(=FTP+MySQL) drinsteht? Habe ich das so richtig verstanden?
Nicht, (0, 1, 2), sondern (1, 2, 3), aber ja. Spart auch wieder immens Speicher gegen deinen VARCHAR, den du da vermutlich hast.


Jetzt, wo das DB-Design klar is (ich geh also davon aus, dass deine kind-Tabelle verschwindet und als Attribut am Backup hängt), kann man sich dem Problem widmen.

Problem 1: Da du ne n:m-Beziehung hast, wirst du wohl zwei Abfragen machen. Der JOIN - wie du schon richtig festgestellt hast - bringt unterschiedlich viele Zeilen pro Backup und kann somit nicht nach Backup seitenweise geblättert werden.
Lösung:
Code:
1:
2:
3:
4:
5:
6:
7:
SELECT backup_id, ... FROM backups LIMIT x, y SELECT ... FROM backups_projects WHERE backup_id IN (...)
Du kannst die Abfrage probieren, zu optimieren, wenn die erste Abfrage z.B. nach backup_id sortiert ist, kannst du mit deren Minimal- und Maximalwert statt dem IN (...) ein BETWEEN min AND max machen. Musst du aber probieren; kp, ob das überhaupt was bringt.

Problem 2: Die erste Abfrage aus Problem 1 wird um eine Unterabfrage erweitert.
Code:
1:
2:
3:
4:
5:
6:
SELECT ... FROM backups WHERE backup_id IN ( SELECT backup_id FROM backup_projects WHERE project_name = 'dein Suchbegriff') LIMIT x, y
Die Frage, ob sich das optimieren lässt, bleibt natürlich offen. Ich hab eben mal überlegt, ob da ein einfacher JOIN reicht, aber ich tippe drauf, dass du ne zweite Instanz von backups brauchst, da du (s.o.) die Spalte backup_id in zwei unterschiedlichen Kontexten brauchst. Probiers einfach aus. EXPLAIN hilft
theHacker ist offline   Mit Zitat antworten
Alt 21.01.2012, 17:06:49   #11 (permalink)
Erfahrener Benutzer

ID: 129556
Lose-Remote

Reg: 28.02.2010
Beiträge: 439
tobomator tobomator tobomator tobomator tobomator tobomator
Standard

Zitat:
Zitat von Gsus Beitrag anzeigen
Hallo,

Tabelle 1: global_backups
snipp...

Aus diesen Tabellen brauche ich nun ein Array, das wie folgt aussieht:
PHP-Code:
1:
2:
3:
4:
5:
6:
7:
array("backup_id" => [ID],
       
"datetime" => [datetime],
       
"kind" => array([=> ftp],
                            [
=> mysql]),
       
"projects" => array([=> "Projekt 1"],
                                 [
=> "Projekt 2"])

...
Gsus
Ich würde folgendes Design wählen:
n ist eine ganze Zahl
ist DATETIME nicht ein reserviertes Wort bei sql ?

Code:
1:
2:
3:
4:
5:
6:
7:
8:
9:
10:
11:
12:
create table global_backups ( backup_id int(n), time_val datetime, primary key (baclup_id) ); create table global_backups_info ( backup_id int(n), kind int(n), project_name varchar(n), foreign key (backup_id) references global_backups(backup_id) );
glaube das verstößt gegen die 3.NF, wenn du nun zu einer ID mehr als 1 project_name hast...
Kind vom Typ int, weil 1 = ftp, 2 = mysql, 3 = ... was in php dann einfach auszuwerten ist.

Code:
1:
2:
3:
select backup_id, time_val, kind, project_name from global_backups as gb, global_backups_info as gbi where gb.backup_id = gbi.backup_id;
Würde man eine 3 Tabelle machen, wo nur die Backup_id mit dem Namen drin stehen, dann müßte auch in der Info dort ein Foreign Key auf die ID in der 3 Tabelle erfolgen. Dann kann man einfach alle project_name's selecten unter einer bestimmten ID, die sicher auch sortierbar wären!

Geändert von tobomator (21.01.2012 um 17:22:41 Uhr)
tobomator ist offline   Mit Zitat antworten
Alt 21.01.2012, 20:08:23   #12 (permalink)
schwankend^^

ID: 215354
Lose-Remote
Reallife

Reg: 22.05.2006
Beiträge: 1.505
Gsus ist einfach richtig nettGsus ist einfach richtig nettGsus ist einfach richtig nettGsus ist einfach richtig nett
Standard

Zitat:
Zitat von theHacker Beitrag anzeigen
Problem 2: Die erste Abfrage aus Problem 1 wird um eine Unterabfrage erweitert.
Code:
1:
2:
3:
4:
5:
6:
SELECT ... FROM backups WHERE backup_id IN ( SELECT backup_id FROM backup_projects WHERE project_name = 'dein Suchbegriff') LIMIT x, y
Okay, vielen Dank! Dein Ansatz für mein erstes Problem klingt plausibel, das zweite wird hiermit jedoch noch nicht gelöst (denke ich zumindest) da ich auch die Möglichkeit haben möchte, nach Backups zu suchen, die sagen wir mal 5 bestimmte Projekte enthalten. Mit deinem Ansatz habe ich in der Subquery allerdings wieder nur einen Datensatz, der nicht mit den anderen verbunden ist.

mfg
Gsus
Gsus ist offline Threadstarter   Mit Zitat antworten
Alt 21.01.2012, 21:07:29   #13 (permalink)
bekämpft die Mächte des Bösen
Benutzerbild von theHacker

ID: 69505
Lose-Remote

theHacker eine Nachricht über ICQ schicken theHacker eine Nachricht über AIM schicken theHacker eine Nachricht über MSN schicken theHacker eine Nachricht über Yahoo! schicken theHacker eine Nachricht über Skype™ schicken
Reg: 20.04.2006
Beiträge: 20.468
theHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes Ansehen
Standard

Zitat:
Zitat von Gsus Beitrag anzeigen
Mit deinem Ansatz habe ich in der Subquery allerdings wieder nur einen Datensatz, der nicht mit den anderen verbunden ist.
Doch, du solltest alle kriegen. Du kannst aber nicht nach mehreren suchen.

Bsp:
Backup 1 enthält Projekte A, B, C.
Backup 2 enthält Projekte A, D.

Suchst du nach Projekt A, kriegst du Backup 1 und Backup 2.
Suchst du nach Projekt B, kriegst du nur Backup 1.
Suchst du nach Projekt D, kriegst du nur Backup 2.

Du kriegst deshalb alle, weil du ja explizit alle Projekte (unabhängig von einer Suche) aus der n:m-Beziehung abfragst (s. zweite Abfrage bei Problem 1).

edit:
Verständlicher: Die Suche schränkt nur nach den Backups ein, nicht nach den BackupProjects-Zeilen. Die werden ausgehend von den Backups nachgeladen.
theHacker ist offline   Mit Zitat antworten
Alt 21.01.2012, 21:45:16   #14 (permalink)
schwankend^^

ID: 215354
Lose-Remote
Reallife

Reg: 22.05.2006
Beiträge: 1.505
Gsus ist einfach richtig nettGsus ist einfach richtig nettGsus ist einfach richtig nettGsus ist einfach richtig nett
Standard

Und wieder habe ich mich unverständlich ausgedrückt

Ich meinte damit: Das result des Subquerys ist nicht mit den zum gleichen Backup gehörigen anderen Datensätzen der gleichen Tabelle verbunden, weshalb ich nicht nach mehreren Projekten suchen kann.

Um dein Beispiel zu benutzen:

Backup 1 enthält Projekte A, B, C.
Backup 2 enthält Projekte A, D.
Backup 3 enthält Projekte A, B, D.

Nun möchte ich nach A und B suchen können und Backup 1 und 3 erhalten, also alle Backups, in denen alle angegebenen Projekte (oder mehr) enthalten sind.

mfg
Gsus
Gsus ist offline Threadstarter   Mit Zitat antworten
Alt 21.01.2012, 23:39:02   #15 (permalink)
bekämpft die Mächte des Bösen
Benutzerbild von theHacker

ID: 69505
Lose-Remote

theHacker eine Nachricht über ICQ schicken theHacker eine Nachricht über AIM schicken theHacker eine Nachricht über MSN schicken theHacker eine Nachricht über Yahoo! schicken theHacker eine Nachricht über Skype™ schicken
Reg: 20.04.2006
Beiträge: 20.468
theHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes AnsehentheHacker genießt hohes Ansehen
Standard

Zitat:
Zitat von Gsus Beitrag anzeigen
Nun möchte ich nach A und B suchen können und Backup 1 und 3 erhalten, also alle Backups, in denen alle angegebenen Projekte (oder mehr) enthalten sind.
Ohne groß nachzudenken würd ich jetzt im Subselect n Auto-JOIN auspacken. Je mehr Projekte im Suchausdruck sind, desto komplexer wird dann die Abfrage.

In dem Fall würde ich dann eher dazutenden, dann du alle ProjectBackups aus der DB holst, die zu einem gesuchten Projekt passen, also in deinem Beispiel
Code:
1:
2:
3:
4:
SELECT backup_id FROM backup_projects WHERE project_name IN ('Projekt A', 'Projekt B') ORDER BY backup_id, project_name ASC
, wobei hier die Besonderheit die Sortierung nach der Backup-ID und danach nach dem Projektnamen is. In PHP gehst du dann der Reihe nach durch und wirst alle Backup-IDs raus, die nicht alle gesuchten Projekte enthalten. Die Abfrage selber würde nämlich nur das Ergebnis "Finde alle Backups, in denen Projekt A oder Projekt B drin is"; du willst aber ein Und.

Das baust du dir dann relativ einfach in PHP. Es kommen der Reihe nach alle Projekte eines Backups, bevor das nächste Backup beginnt. Und die Projektnamen sind auch sortiert, d.h. du weißt genau in welcher Reihenfolge was zu erwarten is.
theHacker ist offline   Mit Zitat antworten
Antwort

Gesponsorte Links

Anzeige


Aktive Benutzer in diesem Thema: 1 (Registrierte Benutzer: 0, Gäste: 1)
 
Themen-Optionen
Ansicht

Forumregeln
Es ist Ihnen nicht erlaubt, neue Themen zu verfassen.
Es ist Ihnen nicht erlaubt, auf Beiträge zu antworten.
Es ist Ihnen nicht erlaubt, Anhänge hochzuladen.
Es ist Ihnen nicht erlaubt, Ihre Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks sind an
Pingbacks sind an
Refbacks sind an


Ähnliche Themen
Thema Autor Forum Antworten Letzter Beitrag
[SQL] Passender Query? tomtom Programmierung 6 13.11.2007 16:11:31
[PHP] MySQL Query sam940 Programmierung 3 08.12.2006 17:36:49


Alle Zeitangaben in WEZ +1. Es ist jetzt 18:18:17 Uhr.