Seite 1 von 2 12 LetzteLetzte
Ergebnis 1 bis 10 von 13

Thema: String als Column Name

  1. #1
    luba ist offline Neuer Benutzer
    Registriert seit
    20.05.2010
    Beiträge
    6

    Standard String als Column Name

    Hallo Leute

    Habe folgendes Problem:

    Ich versuche in einem SELECT Statement die Column Names variabel zu gestalten.

    Nehmen wir an wir hätten eine Table "article" mit z.b. 2 columns "price_eur" und "price_usd".

    Zudem habe ich eine Table "contact" mit der column "currency";

    Ziel ist sowas wie:
    Code:
    SELECT 'price_' || (SELECT currency FROM contact WHERE id = 1) from article;
    So könnte ich den price in der jeweiligen Währung des angegebenen Kontakts bekommen ohne dass ich die Query jemals umbauen müsste.

    Leider bekomme ich dafür nur den string zurück, da Postgres so nicht weiss, das dieser string einen Spaltennamen repräsentiert. Quote ich die Begriffe jedoch nicht als string, kann ich sie nicht concatenaten.

    Das Ergebnis ist also ungefähr so:
    price_chf
    price_chf
    price_chf
    price_chf
    price_chf
    price_chf
    price_chf

    Eine Idee von mir war, den string mit einem Cast als Column zu definieren. So was wie:
    Code:
    ('price_' || 'eur')::column_name
    Leider kenne ich den korrekten Datentyp nicht, wenns überhaupt so einen gibt.

    Natürlich könnte ich das ganze auch mit plpgsql lösen, jedoch sehe ich nicht ein, weshalb man für so eine einfach query grad ne stored procedure bauen soll.


    Hat irgendjemand eine Idee?

  2. #2
    castorp ist offline Erfahrener Benutzer
    Registriert seit
    27.06.2009
    Beiträge
    493

    Standard

    Zitat Zitat von luba Beitrag anzeigen
    Nehmen wir an wir hätten eine Table "article" mit z.b. 2 columns "price_eur" und "price_usd".
    Wenn Dein Modell normalisiert wäre und der Preis in einer Tabelle "price" mit einer Spalte "currency" gespeichert würde, dann hättest Du das ganze Problem nicht - dann wäre es nämlich ein einfacher Join.


    Natürlich könnte ich das ganze auch mit plpgsql lösen, jedoch sehe ich nicht ein, weshalb man für so eine einfach query grad ne stored procedure bauen soll.
    Mit diesem Datenmodell geht es nicht anders.


    Hat irgendjemand eine Idee?
    Ein besseres Datenmodell!
    A SQL query walks into a bar and sees two tables. He walks up to them and says 'Can I join you?'

  3. #3
    akretschmer ist offline Super-Moderator
    Registriert seit
    29.10.2006
    Ort
    Nähe Dresden
    Beiträge
    5.337

    Standard

    Zitat Zitat von luba Beitrag anzeigen
    Hallo Leute

    Habe folgendes Problem:

    Ich versuche in einem SELECT Statement die Column Names variabel zu gestalten.
    Das geht nicht. Nicht mit SQL Das würde gehen mit z.B. plpgsql, aber auch dann nur als dynamisches Query, EXECUTE.

    Der Grund ist simpel: Der Planner hat einen Plan zu erstellen. Das kann er nicht, wenn nicht schon vor Ausführung der Abfrage die Struktur des Ergebnisses feststehen würde.

    In Kurz: vergiß es.

    In Lang: überdenke Dein Design.

    Andreas
    --
    ads Das hatte dir akretschmer gestern schon gesagt und siehe da sobald du das machst, funktioniert es ;-)
    https://www.xing.com/profile/Andreas_Kretschmer7

  4. #4
    luba ist offline Neuer Benutzer
    Registriert seit
    20.05.2010
    Beiträge
    6

    Standard

    Merci für die Antworten.

    Bezüglich Datenmodell: Ich hätte vielleicht vorwegnehmen sollen, dass mir bewusst ist, dass mein Datenmodell jeglicher Normalisierung widerspricht und sehr unschön ist. Leider gibt es gute Gründe für mich dies so zu tun. Meine Applikation hat mittlerweile Dimensionen angenommen, welche Änderungen in der Basis SEHR aufwändig machen. Ich habe mir das Design lange überlegt und auch die normalisierte Variante bereits als Diagramm skizziert. Ich hatte die Wahl zwischen der edlen, aufwändigen oder der einfachen, dafür etwas hässlichen (und mindestens um den Faktor 10 schnelleren) Lösung. Es ist lediglich eine Zeitfrage.

    Ich bin bereits daran, eine dynamische Query mit EXECUTE zusammenzubasteln. Werde meine Lösung hier posten wenn ich fertig bin (ich hasse Problem-Threads ohne Lösung ^^).

  5. #5
    castorp ist offline Erfahrener Benutzer
    Registriert seit
    27.06.2009
    Beiträge
    493

    Standard

    Zitat Zitat von luba Beitrag anzeigen
    und mindestens um den Faktor 10 schnelleren
    Vermuteter Faktor 10, oder hast Du das wirklich getestet?
    A SQL query walks into a bar and sees two tables. He walks up to them and says 'Can I join you?'

  6. #6
    ads
    ads ist offline Super-Moderator
    Registriert seit
    08.02.2006
    Ort
    MD
    Beiträge
    4.020

    Standard

    Bezugnehmend auf deine Wahl zwischen Normalisierung oder nicht: nun stehst du vor dem Problem, Aufgaben lösen zu müssen, wie es in einer normalisierten Variante wohl nicht geben würde.
    Xandrian: Kurz gesagt: Du hast ein falsches Konzept und willst nicht auf ads hören

    Jetzt NEU: PostgreSQL - Datenbankpraxis für Anwender, Administratoren und Entwickler

    PostgreSQL Service & Support

  7. #7
    luba ist offline Neuer Benutzer
    Registriert seit
    20.05.2010
    Beiträge
    6

    Standard

    Vermuteter Faktor 10, oder hast Du das wirklich getestet?
    Schwierig zu testen, dafür müsste ichs ja beinahe implementieren.

    Der Faktor basiert auf Schätzungen, die ich anstellte, nachdem ich für beide Möglichkeiten Klassendigramme skizziert und die wichtigsten Relationen auch gleich als SQL Code implmentiert hatte.

    Das Zusammenbauen der Relationen in SQL ist die eine Sache.....der grosse Aufwand entsteht dann erst beim Anpassen des php-Codes. Stell dir eine Informatikbude mit eigenem CMS (in php) und ca. 10'000 Kunden vor. Das gesamte Buchhaltungskonzept war ursprünglich für eine Währung vorgesehen (etwas kurzsichtig ... ich war auch nicht von Anfang an dabei). Änderungen in den fundamentalen Tabellen der Buchhaltung ziehen explosionsartigen Aufwand und Anpassungen des ganzen CMS nach sich. Mit anderen Worten: Mit der normalisierten Version müsste ich wirklich die gesamte Buchhaltung umbauen, da bliebe fast kein Stein auf dem anderen. Während diesen Umstellungen muss das Buchhaltungssystem auch noch nahtlos weiterfunktionieren.

    Wir können mit grosser Sicherheit sagen, dass wir nie mehr Währungen als EUR, USD und GBP nutzen werden. Somit ist diese Sache langfristig geritzt. Ich möchte in Sachen Kurzsichtigkeit nicht die selben Fehler machen wie meine Vorgänger, aber ich denke, dass diese Lösung einen akzeptablen Kompromiss darstellt.

    Mit der einfachen Version bin ich mit einigen Anpassungen über den Berg.

    Bezugnehmend auf deine Wahl zwischen Normalisierung oder nicht: nun stehst du vor dem Problem, Aufgaben lösen zu müssen, wie es in einer normalisierten Variante wohl nicht geben würde.
    Das stimmt so wohl und war auch zu erwarten. Bisher ist dies jedoch das einzige Problem, das sich mit dieser Variante stellt und es sieht nach einem in Kauf zu nehmenden Aufwand aus.
    Geändert von luba (25.05.2010 um 11:31 Uhr)

  8. #8
    luba ist offline Neuer Benutzer
    Registriert seit
    20.05.2010
    Beiträge
    6

    Standard

    So.

    Hier wäre mal meine Lösung. Wem's zu dirty ist: Bitte die Augen zuhalten.

    Code:
    CREATE FUNCTION get_article_price_by_contact(i_article_id integer, i_contact_id integer) RETURNS numeric
        AS $$
    DECLARE
            price numeric;
            currency_code varchar;
    BEGIN
            currency_code := (SELECT code FROM currency WHERE id = (SELECT currency_id FROM contact WHERE id = i_contact_id));
                    EXECUTE 'SELECT price_' || currency_code || ' FROM article WHERE id = ' || i_article_id INTO price;
            RETURN price;
    END;
    $$
        LANGUAGE plpgsql;
    Nun kannn ich also mit einem einfachen
    Code:
    SELECT get_article_price_by_contact(1,1);
    gemütlich den jeweiligen Preis in der richtigen Währung holen.

    Für mich ist das Problem zufriedenstellend gelöst. Danke für die Diskussion.

  9. #9
    ads
    ads ist offline Super-Moderator
    Registriert seit
    08.02.2006
    Ort
    MD
    Beiträge
    4.020

    Standard

    Zitat Zitat von luba Beitrag anzeigen
    Während diesen Umstellungen muss das Buchhaltungssystem auch noch nahtlos weiterfunktionieren.
    Dafür hat man Entwickler-, Test-, Staging- und Produktivsysteme.
    Auf einem Livesystem entwickelt man nicht. Niemals.


    Wir können mit grosser Sicherheit sagen, dass wir nie mehr Währungen als EUR, USD und GBP nutzen werden.
    Warten wir, bis der EUR an Wert verliert und die Chinesem mit den CNY oder die Russen mit dem RUB eine Rolle spielen.
    Xandrian: Kurz gesagt: Du hast ein falsches Konzept und willst nicht auf ads hören

    Jetzt NEU: PostgreSQL - Datenbankpraxis für Anwender, Administratoren und Entwickler

    PostgreSQL Service & Support

  10. #10
    luba ist offline Neuer Benutzer
    Registriert seit
    20.05.2010
    Beiträge
    6

    Standard

    Zitat Zitat von ads Beitrag anzeigen
    Dafür hat man Entwickler-, Test-, Staging- und Produktivsysteme.
    Auf einem Livesystem entwickelt man nicht. Niemals.
    Kann ich nur zustimmen. Trotzdem zeigt die Praxis, dass man auch mit dem besten Unit-Testing selten alle Fälle abdecken kann und leider unterscheiden sich Testumgebungen oft leicht von Livesystemen.
    Wir sprechen hier davon, das Herzstück unseres CMS auszutauschen. Das wird definitiv nicht einfach über die Bühne gehen.

    Warten wir, bis der EUR an Wert verliert und die Chinesem mit den CNY oder die Russen mit dem RUB eine Rolle spielen.
    Na gut - stattgegeben ^^. Aber diese Erweiterungen wären danach Peanuts.

Seite 1 von 2 12 LetzteLetzte

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •  

Links: Tobias Bauer - IT- und Funkdienstleistungen   -   Bilderrahmen-kaufen.de - Der Onlineshop für Bilderrahmen & Fotorahmen   -   Funkforum