Juni 15, 2021, 22:04:39

Neuigkeiten:

Wenn ihr euch für eine gute Antwort bedanken möchtet, im entsprechenden Posting einfach den Knopf "sag Danke" drücken!


Altersberechnung

Begonnen von BikeArno, März 05, 2021, 11:41:07

⏪ vorheriges - nächstes ⏩

BikeArno

Hallo,

ich möchte aus Geburtsdatum und aktuellem Datum das Alter in einer Abfrage errechnen:

A_Alter: DatDiff("jjjj";[A_GeburtsdatumTN];Datum())+(Format(Datum();"mmtt")<Format([A_GeburtsdatumTN];"mmtt"))
Leider gibt es auch Datums-Felder, die leer sind. Das Ergebnis ist dann #Fehler in der Abfrage.

Kann ich verhindern, dass diese Fehlermeldung erscheint und die zelle stattdessen leer bleibt?

Gruß

MzKlMu

März 05, 2021, 12:53:34 #1 Letzte Bearbeitung: März 05, 2021, 13:02:10 von MzKlMu
Hallo,
so:
A_Alter: Wenn([A_GeburtsdatumTN] Ist Null;Null;DatDiff("jjjj";[A_GeburtsdatumTN];Datum())+(Format(Datum();"mmtt")<Format([A_GeburtsdatumTN];"mmtt")))
Übersetzt:
Wenn Datum leer (Null) ist, lasse das Feld leer (Null), wenn nicht, rechne das Alter.


Hinweis:
Null ist nicht die Zahl Null, Null ist einfach ein leeres Feld.

Hinweis 2:
Gewöhne Dir ab, bei Access von Zellen zu sprechen, das irritiert, weil man bei Zellen an Excel denkt.
Bei Access gibt es Felder/Spalten und Datensätze (Zeilen).
Gruß
Klaus

andyfau

Hallo,
ich habe den Code gerade mal ausprobiert. Er funktioniert tadellos, wenn das Feld A_GeburtsdatumTN ordentlich als Datumsfeld definiert ist. Es wird gerechnet wenn ein gültiges Datum drin steht und das Ergebnis bleibt leer, wenn das Geburtsdatum leer ist. Es muss also irgendwas im Ausgangsfeld stehen, womit Access nicht rechnen kann.
Gruß
Andreas

BikeArno

Danke vielmals für die Hinweise. Ich denke auch, dass es eigentlich funktionieren müsste. Aber:

Leider bleibt die Fehlermeldung bestehen. Ich vermute, das leere Feld (bei fehlenden Datumsangaben ist es optisch leer) wird nicht als leer erkannt, auch wenn es definitiv leer ist...

Das ursprüngliche Feld ist in der Ursprungstabelle korrekt als Datum formatiert. Die Abfrage hier bezieht sich aber auf eine UNION-Abfrage, in der dieses Datumsfeld vorkommt. Diese UNION-Abfrage kann man sich leider nicht im Entwurfsmodus anzeigen lassen, um das Datumsformat zu prüfen. Oder kann man innerhalb der UNION-Abfrage diese Formatierung vornehmen?

crystal

Ich würde das ganz pragmatisch so testen:
Abfrage komplett kopieren,
in der Kopie erst den Teil vor UNION löschen und testen
dann den Teil nach UNION löschen und testen.

Wenn du das Datumsfeld nur in einem Teil der Union formatieren willst, stimmen die Datentypen wohl doch nicht exakt überein...

Eine FORMAT-Anweisung sollte auch in der Union-Abfrage möglich sein.

Der Datenfeld-Typ "Datum/Uhrzeit" in der Tabellen-Definition ist eine Sache. Sie bestimmt, wieviel Bytes verwendet werden (ist glaub immer die Anzahl der Sekunden ab 1.1.1900 oder so). Eine andere Sache ist das Datums-Format (z. B. "Datum kurz"). Hier wird festgelegt, wie der Feldinhalt optisch dargestellt, also beim Lesezugriff umgewandelt  wird.

Probier auch mal statt "ist Null" "ist leer" oder NZ(datumsfeld,"") oder ISTNULL(Datumsfeld) oder ISTLEER(Datumsfeld) oder (Code von MzKlMu angepasst):

A_Alter: Wenn(NZ([A_GeburtsdatumTN],"") = "");"";DatDiff("jjjj";[A_GeburtsdatumTN];Datum())+(Format(Datum();"mmtt")<Format([A_GeburtsdatumTN];"mmtt")))

Ich denke, "ist Null" funktioniert nur dann, wenn das Feld noch nie "angefasst" wurde. Wenn da mal was drin stand und gelöscht wurde, könnte tatsächlich 0 drin stehen. Bin da aber etwas unsicher.
Wer Fehler in meinen Antworten findet, darf sie behalten, muss sie aber kommentieren. ;-)
Dies ist keineswegs arrogant gemeint, sondern soll nur unterstreichen, dass meine Antworten - natürlich - nicht immer fehlerfrei sind und sein können.
Devise: bitte immer erst selbst probieren!

Aus gesundheitlichen Gründen nur noch selten dabei...

BikeArno

Hallo crystal,

ich werde das mal probieren, danke vielmals. Der angepasste Code allerdings hat, so sagt mir Access, einen Syntaxfehler? Ich finde ihn aber nicht...

MzKlMu

März 05, 2021, 15:03:46 #6 Letzte Bearbeitung: März 05, 2021, 16:36:47 von MzKlMu
Hallo,
wie bereits gesagt, ein leeres Datusfeld führt nicht zu einem Fehler. Die Wenn() Bedingung wie von mir vorgeschlagen ist somit überflüssig. Der Fehler muss eine andere Ursache haben.

Der Datenfeld-Typ "Datum/Uhrzeit" ist eine Zahl des Typs Double.
Vor dem Komma ist die Anzahl der Tage die seit dem 30.12.1899 vergangen sind. Die 1 entspricht somit dem 31.12.1899.
Nach dem Komma ist der dezimale Anteil eines Tages.
0,5 = 12 uhr
0,25 = 6 Uhr
Der heutige Tag 05.03.2021 14:50 Uhr wird als Kommazahl so gespeichert:
44260,6180555556

In dem Feld kann also keine 0 (die Zahl) stehen, denn mit Format würde hier als Datum der 30.12.1899 interpretiert werden.

Zitat von: undefinedIch denke, "ist Null" funktioniert nur dann, wenn das Feld noch nie "angefasst" wurde.
Nein, ein leeres Feld ist Null. Es ist auch kein "" (Leerstring). Ob in dem Feld mal was drin stand oder nicht spielt keine Rolle. Um ein Feld wirklich zu leeren, kann/sollte man auch Null zuweisen. Also so:
Me.Feldname = NullDas funktioniert auch mit einem Datumsfeld.
Man sollte auch auf keinen Fall "" zuweisen, denn damit ist das Feld nur scheinbar leer und eine Prüfung auf IstNull (VBA) oder Ist Null (SQL) würde nicht greifen.

@BikeArno
Zitat von: undefinedDer angepasste Code allerdings hat, so sagt mir Access, einen Syntaxfehler?
Wie soll man den finden, wenn man den Code nicht sieht ?  ::)

Zeige bitte mal die Union Abfrage.
Gruß
Klaus

BikeArno

Zitat von: MzKlMu am März 05, 2021, 15:03:46Wie soll man den finden, wenn man den Code nicht sieht ? 

Hallo,

die Erklärung oben mit dem Datum ist interessant, wusste ich so noch nicht. Nur vom Rest verstehe ich nur die Hälfte...

Der Code stand oben:
A_Alter: Wenn(NZ([A_GeburtsdatumTN],"") = "");"";DatDiff("jjjj";[A_GeburtsdatumTN];Datum())+(Format(Datum();"mmtt")<Format([A_GeburtsdatumTN];"mmtt")))

Die Union-Abfrage geht über mehrere Seiten und sieht so aus, dass aus mehreren Tabellen Felder vereint werden, u.a. ein Datumsfeld (Geburstag). In 10 Tabellen gibt es dieses, in 2 Tabellen fehlt dieses Feld, weshalb in der Union-Abfrage dieses Feld leer ist. In der UNION-Abfrage ersetzt durch "". In der Union-Abfrage selbst habe ich das Datumsfeld (Geburstag) nicht als solchens formatiert (keine Ahnnung, wie das geht).

Gruß

andyfau

Versuche mal:

A_Alter: Wenn(Wert(Nz([A_GeburtsdatumTN];0))=0;0;DatDiff("jjjj";[A_GeburtsdatumTN];Datum())+(Format(Datum();"mmtt")<Format([A_GeburtsdatumTN];"mmtt")))
Gruß
Andreas

MzKlMu

März 05, 2021, 16:23:05 #9 Letzte Bearbeitung: März 05, 2021, 16:37:41 von MzKlMu
Hallo,
wie ich in #6 schon schrieb, führt die die Zuweisung von "" zu einem Fehler. Bei der Union wird dadurch aus dem Datumsfeld ein Text, was falsch ist.
Wie ich auch schon in #6 schrieb, sollte man Felder durch Zuweisung von Null leeren, was dann nicht zu einer Änderung des Datentyps führt. Dann dürfte auch die Altersberechnung ohne Klimmzüge von Statten gehen.
Zeige mal einen Ausschnitt aus Deiner Union wo man die Zuweisung von "" sieht.

Übrigens, ob der Datentyp sich durch die Abfrage ändert, lässt sich relativ einfach prüfen.
Ein echtes Datum wird immer rechtsbündig angezeigt. Wird aus dem Datum ein Text ist es linksbündig.

Und (nicht) nebenbei:
Wer in einer Datenbak Unionabfragen braucht, hat oftmals die Struktur (Datenmodell) falsch angelegt. Erst recht über 12 Tabellen.
Warum hast Du da 12 Tabellen, wenn Du diese doch mit einer Union zusammenpappst ?
Gruß
Klaus

Beaker s.a.

Hallo Arno,
Hört verdächtig nach Excel-Denke an.
Wie Klaus schon vermutet hat liegt das Problem hier wohl im Datenmodell.
Auch wenn es höchstwahrscheinlich an den Tatbestand der Körperverletzung
grenzt  ;), zeige uns doch mal ein Bild des Beziehungsfensters.

gruss ekkehard
--
Beaker s.a., der lieber an seinem eigenen Projekt arbeiten würde/sollte, aber irgendwie immer gerne seinen Senf dazu gibt ;-)
S.M.I².L.E.

BikeArno

Zitat von: MzKlMu am März 05, 2021, 16:23:05Wer in einer Datenbak Unionabfragen braucht, hat oftmals die Struktur (Datenmodell) falsch angelegt. Erst recht über 12 Tabellen.
Warum hast Du da 12 Tabellen, wenn Du diese doch mit einer Union zusammenpappst ?

Hallo,

ich gebe euch uneingeschränkt recht, dass die Datenbank Körperverletzung ist. Ich habe die Datenbank leider geerbt und kann sie aus verschiedenen Gründen nicht vollständig neu aufbauen. Ich versuche aber, zu retten, was zu retten ist. Die separaten Tabellen bekomme ich von extern, die sind also vorgegeben.

Bei der Union-Abfrage werden nur ausgewählte Felder vereint, eine kleine Auswahl aus den 12 Tabellen.

Ja Klaus, das betreffende Datumsfeld wird linksbündig angezeigt, also Text.

Die Union sieht beispielhaft wie folgt aus:

SELECT [ID-Nummer] as ID,"","","","","","", Mitgliedstatus AS v_Mitglied, Geburtstag AS v_Geburtstag,"","", [...]
FROM tbl_1

UNION SELECT [ID-Nummer] as ID,"","","","","","", Mitgliedstatus AS v_Mitglied, Geburtstag AS v_Geburtstag,"","", [...]
FROM tbl_2;

Gruß

BikeArno

Zitat von: andyfau am März 05, 2021, 16:05:05Versuche mal:

A_Alter: Wenn(Wert(Nz([A_GeburtsdatumTN];0))=0;0;DatDiff("jjjj";[A_GeburtsdatumTN];Datum())+(Format(Datum();"mmtt")<Format([A_GeburtsdatumTN];"mmtt")))
Gruß
Andreas

Hallo Andreas,

Die vorläufige Rettung! Dieser Code macht genau das, was ich für die Problemlösung benötige. Er schreibt mir eine "0" in das Feld, wo vorher #Fehler stand. Danke!

Gruß