Announcement

Collapse
No announcement yet.

FilterExpression

Collapse
X
  • Filter
  • Time
  • Show
Clear All
new posts

  • FilterExpression

    Hallo,
    muss mein altes Thema nochmal aufgreifen. Da ging es um Strings. Jetzt aber um Datum.
    Aus einer Tabelle gewinne ich eine DataView, die wiederum den Source für ein DataGridView darstellt. Auf die DataView angewandte Filter sind sofort im Grid sichtbar.
    Eine Column (C4133) ist in der DB (MySql) as datetime definiert. Werte darin z.B. 2020-04-10 10:00:00
    Der Filter, um z.B. alle Datensätze des aktuellen Quartals (ab 01.01.2020) anzuzeigen, lautet
    Code:
    Dim akt As Date = CDate("1." & ((CInt(Math.Round((Date.Now.Month + 0.9) / 3)) - 1) * 3) + 1 & "." & Date.Now.Year).AddDays(-1)
    trmView.RowFilter = "C4133>#" & akt & "#"
    Vielleicht ein bisserl umständlich, aber besser hab ich's bislang nicht hinbekommen.

    Einen anderen Filter zu erzeugen, nämlich die Anzeige der Datensätze mit dem heutigen Datum, will mir einfach nicht gelingen:
    Code:
    trmView.RowFilter = "C4133=" & now
    Ich habe für now schon alle Datentypen und Formatierungen durchprobiert, aber nichts funktioniert. Könnt ihr mir unter die Arme greifen?
    Danke. Grüße Norbert

  • #2
    Bei Datumswerten auf Gleichheit zu prüfen ist immer schlecht bzw. schwierig. Wen dein now z.b. DateTime.Now entspricht hast du die volle Auflösung inclusive Microsekunden. Da wird nie etwas gleich sein. Soviel Zufall gibt es nicht. Üblicherweise flält man auch noch über systemspezifische Datumsdarstellungen. Die interne Datumsdarstellungen vom MySql ist vermutlich anders als die von .NET. und beim dann nötigen internen hin und herrechnen kommen da in der Darstellung dann ein paar Mikrosekunden unterschied raus. Und beim vergleichen auf Gleichheit gilt dann knapp daneben ist auch vorbei.

    Beim Vergleichen kann man dann versuchen beide Seiten gleich zu normieren damit die Dinge sicher vergleichbar werden. Das ist bei RowFilter aber möglicherweise schwierig. Die Kontrolle über die Daten in der Column werden dir möglicherweise fehlen. Hab da auch gerade nicht alle Möglichkeiten von RowFilter im Kopf.

    Darum wäre die unspezifischste aber in den meisten Fälle sicherste Methode wenn du Daten wie zum Beispiel mit dem heutigen Datum vergleiche willst die mit einem von-bis vergleich mit einem Delta also z.B.
    Code:
    c4133 >= DateTime.Now.Today AND c4133 < DateTime.Now.Today.AddDays(1)
    zu machen. Das sollte dir alle Daten von heute liefern unabhängig des Zeitanteils im Datum.

    Comment


    • #3
      Vielen Dank Ralf. Ist immer wieder eine Freude, wie schnell Du reagierst.
      Nichts zu machen. Erstmal:
      Code:
      Date.Now = DateTime.Now = #3/28/2020 01:18:18 PM#
      Date.Today = DateTime.Today = #3/28/2020 12:00:00 AM#
      Date.Today ist schon mal ein sehr guter Ansatz, da ich die Zeit um Mitternacht bekomme. Habe erst jetzt durch Dich den Unterschied zw. Now und Today begriffen!
      Komisch ist nur, wenn ich trmView.RowFilter = "C4133>=" & Date.Today oder

      Dim now As Date = Date.Today
      trmView.RowFilter = "C4133=" & now


      mache, wirft er mir die Exception "Das Token '.' kann an Position 13 nicht interpretiert werden."
      Mein Beispiel oben in #1 mit akt ist doch aber eigentlich auch nichts anderes, oder? Und das funktioniert.
      In c4133 steht 2020-04-10 10:00:00 als MySql DateTime.
      Hast Du noch eine Idee? Ich muss lediglich aus der DB die Rows anzeigen, wo in c4133 das Tagesdatum steht. Das sind alle vom Server gelieferten Termine für den heutigen Tag (Pflicht für meine Zertifizierung). Uhrzeiten spielen keine Rolle.


      Zuletzt editiert von strzata; 28.03.2020, 15:01.

      Comment


      • #4
        Sieht so aus als würde man gezwungen sein bei RowFilter zwangsweise immer mit strings zu arbeiten ohne automatische Hilfe bei anderen Datentypen.
        Sowohl meine Kenntnisse über den RowFilter Syntax als auch VB halten sich in Grenzen.

        Soweit ich das in C# nachstellen und dann nach VB übersetzt habe sollte das was ich meinte in VB Syntax etwa so aussehen.


        Code:
        Dim now As Date = Date.Today
        trmView.RowFilter = $"[C4133] >= #{now.ToString("yyyy-MM-dd")}# AND [C4133] < #{now.AddDays(1).ToString("yyyy-MM-dd")}#"

        Comment


        • #5
          Ralf - Du bist der Grösste!!! Unglaublich!
          Der Code ist für mich völlig unverständlich (habe noch nie ein $ vor irgendwas gesetzt und {} nur bei einer String-Liste verwendet) - aber es funktioniert tadellos!
          Von Dir hab ich schon eine ganze Sammlung solcher exotischer Tricks gesammelt. Es wäre ein Eldorado für alle, wenn Du Deine Trickkiste mal wie die Büchse der Pandora öffnen würdest ...
          Vielen vielen Dank und ein schönes Wochenende
          Norbert

          Comment


          • #6
            Hab nochmal gegoogelt, um mein Gewissen zu beruhigen, dass ich Ralf mit etwas belästigt habe, was ich hätte selbst finden können. Aber ein solcher Beispielcode ist im gesamten Netz nirgends zu finden. Es ist wirklich der Hammer!

            Comment


            • #7
              Doch es ist alles im Netz zu finden. Problem ist üblicherweise das es die Dinge in der Kombination im Netz nicht gibt. Oder zumindest nicht in der Kombination die dem eigenen Wissensstand entspricht um zu erkennen das es eine Lösung des eigenen aktuellen Problems ist. Da hilft üblicherweise allgemeine IT Erfahrung und andere Entwickler. Wer täglich mit anderen Entwicklern zu tun hat ist da klar im Vorteil. Das können Foren nur begrenzt ersetzen.

              Letztlich ist hier aber nichts magisches dahinter. Das eine Feature nennt sich interpolierte Strings. Das halte ich fast für ein Standardwerkzeug. Solltest du dir auf jedenfall mal ansehen. Das ergibt schnell deutlich besser lesbareren Code als Stringkonkatenierung. Hier mag es etwas unschön aussehen was aber eher am hässlichen Expression Syntax der im DataTable/DataView Umfeld benutz wird. Ersteres kannte ich (und sieht in VB glücklicherweise genauso aus wie in C#) letztere Quelle habe ich kurz zu rate gezogen um mir den Syntax zu erarbeiten. Mehr war da nicht.

              Da hässlichste oder unverständlichste an dieser Stelle ist am ehesten ein Spaltenname wie C4133. Das wird wirklich furchtbar

              Comment


              • #8
                Erst jetzt gesehen, weil man keine Benachrichtigung erhält, wenn jemand geantwortet hat. Ein echtes Manko in diesem Forum. Aber es ist von den kompetenten Antworten her, den Reaktionsgeschwindigkeiten und den netten Leuten hier meine liebste und allererste Wahl!
                Übrigens: meine Columns beginnen alle mit "C" und sind vierstellig. Bei den über hundert Tabellen im Projekt erkenne ich daran auch gleich, zu welcher Tabelle sie gehören. Ist seit 20 Jahren so gewachsen. Was stört Dich daran?

                Comment


                • #9
                  Erst jetzt gesehen, weil man keine Benachrichtigung erhält, wenn jemand geantwortet hat. Ein echtes Manko in diesem Forum.
                  Das kann man in seinem Profil ein-/ausschalten

                  Die Tabellen beginnen dann mit T und sind auch zweistellig?

                  Damit lässt sich schlecht arbeiten sie sind schlecht wartbar. Man weiß nicht wozu die Tabelle dient, sieht den Columns nicht ihren möglichen Inhalt an. Bei Nutzung eines OR-Mappers sehen dann die Klassen "komisch" aus, bzw. man müsste extra Namen vorgeben.
                  Man müsste eine Synopse führen, in dem die Bedeutung aufgelistet ist
                  Für ein Hobbyprojekt mag es angehen.
                  Zuletzt editiert von Christian Marquardt; 28.04.2020, 15:31.
                  Christian

                  Comment


                  • #10
                    Übrigens: meine Columns beginnen alle mit "C" und sind vierstellig. Bei den über hundert Tabellen im Projekt erkenne ich daran auch gleich, zu welcher Tabelle sie gehören. Ist seit 20 Jahren so gewachsen. Was stört Dich daran?
                    Weil sie nicht sagen wofür sie gut sind und was ihr Inhalt bedeutet. Das ist für jemand nur wartbar mit viel Erfahrung in diesem Model und einer irgendwo niedergeschriebenen Dokumentation. Von einem ordentlich benammstes Model sollte sich jeder mit mittelprächtigem allgemeinen Verständnis ein Bild machen können. Beispiel wenn eine Spalte "AdresseID" in der Tabelle "Person" heißt dann kann ich mir ziemlich sicher sein das es irgendwo eine Adresse Tabelle gibt und das hier der Fremdschlüssel auf diese Tabelle ist. Wenn jetzt der Fremdschlüssel hier noch so heißt wie der Primärschlüssel dort hat man das sofort begriffen einschließlich der Zusammenhänge zwischen Tabellen. In deinem Fall müßte man irgendwie erraten das "C1234" aus "T17" auf "C2345" in "T99" referenziert wenn man überhaupt erkennt das bestimmte Dinge woanders gespeichert sind. Im schlimmsten Fall braucht man zwingend irgendwelche relationallen graphischen Modelle um das nachverfolgen zu können. Da ist es doch viel einfach wenn man das schon am Namen der Dinge erkennt.

                    Comment


                    • #11
                      Weil sie nicht sagen wofür sie gut sind und was ihr Inhalt bedeutet
                      Bin vor 30 Jahren bei einem Programmierer in die Schule gegangen, der mir beigebracht hat, bei einem kommerziellen Produkt so viel wie möglich zu verstecken. Aber ich gebe Dir Recht. Sollte mein Schwiegersohn nach meinem Ableben das Projekt weiterführen wollen, wird er es schwer haben. Obwohl - es ist alles akribisch dokumentiert ...

                      Comment

                      Working...
                      X