von iTob » Mo 6. Mär 2017, 18:08
Hi ionas,
genau über diese Variante kann man (im Prinzip) nur neun Argumente verarbeiten. Mit ein paar Tricks gehen auch mehr, siehe z.B.
http://tex.stackexchange.com/q/2132/4918
Aber ich gebe "Gast" recht, das in dem Fall eine andere Syntax sicher die bessere Variante wäre. Ich habe hier mal fix skizziert, wie man das mit LaTeX3 machen könnte:
\documentclass{scrartcl}
\usepackage[utf8]{inputenc}
\usepackage[T1]{fontenc}
\usepackage{xparse}
\ExplSyntaxOn
% Variable für Liste mit allen Personen
\seq_new:N \g_ionas_persons_seq
% Befehl zum Anlegen einer neuen Person
% - #1: ID (nur Buchstaben)
% - #2: Key-Value-Paare als Komma-getrennte Liste
\NewDocumentCommand { \newPerson } { m m } {
% neue Person in der Liste aller Personen registrieren, wenn ID nicht vorhanden
\seq_if_in:NnTF \g_ionas_persons_seq { #1 } {
% TRUE: ID ist bereits vergeben
\ERROR ID ~ bereits ~ vergeben!
} {
% FALSE: ID ist noch frei
\seq_gput_right:Nn \g_ionas_persons_seq { #1 }
% neue Property-Liste (basierend auf der ID)
\prop_new:c { g_ionas_person_with_ID_#1_prop }
% Liste der Schlüssel-Wert-Paare durchlaufen
\clist_map_inline:nn { #2 } {
% \#\#1 = ##1\\
\ionas_parse_key_value:w ##1 \q_stop
\prop_gput:cVV { g_ionas_person_with_ID_#1_prop }
\l_ionas_current_key_tl
\l_ionas_current_value_tl
}
% Prüfen ob alle nötigen Werte angeben wurden
\clist_map_inline:nn { name, given-name, number } {
\prop_if_in:cnF { g_ionas_person_with_ID_#1_prop } { ##1 } {
\ERROR Wert ~ für ~ '##1' ~ fehlt.
}
}
}
}
% Variablen und Befehle zum Einlesen von Schlüssel-Wert-Paaren
\tl_new:N \l_ionas_current_key_tl
\tl_new:N \l_ionas_current_value_tl
\cs_new:Npn \ionas_parse_key_value:w #1 = #2 \q_stop {
\tl_set:Nn \l_ionas_current_key_tl { #1 }
\tl_trim_spaces:N \l_ionas_current_key_tl
\tl_set:Nn \l_ionas_current_value_tl { #2 }
\tl_trim_spaces:N \l_ionas_current_value_tl
% K = \l_ionas_current_key_tl \\
% V = \l_ionas_current_value_tl \\
}
% Befehl zum Ausgeben aller Personen
\NewDocumentCommand { \getAllPersons } { } {
\begin{itemize}
\seq_map_inline:Nn \g_ionas_persons_seq {
\item
\getPersonInfo { ##1 } { given-name }
\c_space_tl
\getPersonInfo { ##1 } { name }
}
\end{itemize}
}
% Befehl zum Auslesen einer Bestimmten Eigenschaft
% - #1: ID
% - #2: Eigenschaft
\NewDocumentCommand { \getPersonInfo } { m m } {
\prop_item:cn { g_ionas_person_with_ID_#1_prop } { #2 }
}
\ExplSyntaxOff
\begin{document}
\minisec{Neue Personen anlegen}
(führt nicht zu einer Text-Ausgabe)
\newPerson{mmustermann}{
name = Mustermann,
given-name = Max,
number = 12345,
}
\newPerson{jdoe}{
name = Doe,
given-name = John,
number = 555123,
cuntry = USA,% Diese Angabe ist optional
}
\newPerson{jdoe2}{
name = Doe,
given-name = Jane,
number = 555321,
cuntry = USA,% Diese Angabe ist optional
}
% Das Folgende erzeugt einen Fehler, weil keine Nummer angeben ist
%\newPerson{ssorglos}{
% name = Sorglos,
% given-name = Susi,
%}
% Das Folgende erzeugt einen Fehler, weil die ID schon vergeben ist
%\newPerson{mmustermann}{
% name = Mustermann,
% given-name = Martin,
% number = 54321,
%}
\minisec{Alle Personen ausgeben}
\getAllPersons
\minisec{Bestimmte Infos abfragen}
Name: \getPersonInfo{mmustermann}{name}\\
Matrikelnummer: \getPersonInfo{jdoe}{number}
\end{document}
Für ausführliche Erklärungen fehlt mir grad die Zeit aber für einen Einstig in LaTeX3 schau gern mal in meinem Blog vorbei:
http://tobiw.de/tbdm/funktionssymbole
Viele Grüße
Tobi
Hi ionas,
genau über diese Variante kann man (im Prinzip) nur neun Argumente verarbeiten. Mit ein paar Tricks gehen auch mehr, siehe z.B. http://tex.stackexchange.com/q/2132/4918
Aber ich gebe "Gast" recht, das in dem Fall eine andere Syntax sicher die bessere Variante wäre. Ich habe hier mal fix skizziert, wie man das mit LaTeX3 machen könnte:
[code]\documentclass{scrartcl}
\usepackage[utf8]{inputenc}
\usepackage[T1]{fontenc}
\usepackage{xparse}
\ExplSyntaxOn
% Variable für Liste mit allen Personen
\seq_new:N \g_ionas_persons_seq
% Befehl zum Anlegen einer neuen Person
% - #1: ID (nur Buchstaben)
% - #2: Key-Value-Paare als Komma-getrennte Liste
\NewDocumentCommand { \newPerson } { m m } {
% neue Person in der Liste aller Personen registrieren, wenn ID nicht vorhanden
\seq_if_in:NnTF \g_ionas_persons_seq { #1 } {
% TRUE: ID ist bereits vergeben
\ERROR ID ~ bereits ~ vergeben!
} {
% FALSE: ID ist noch frei
\seq_gput_right:Nn \g_ionas_persons_seq { #1 }
% neue Property-Liste (basierend auf der ID)
\prop_new:c { g_ionas_person_with_ID_#1_prop }
% Liste der Schlüssel-Wert-Paare durchlaufen
\clist_map_inline:nn { #2 } {
% \#\#1 = ##1\\
\ionas_parse_key_value:w ##1 \q_stop
\prop_gput:cVV { g_ionas_person_with_ID_#1_prop }
\l_ionas_current_key_tl
\l_ionas_current_value_tl
}
% Prüfen ob alle nötigen Werte angeben wurden
\clist_map_inline:nn { name, given-name, number } {
\prop_if_in:cnF { g_ionas_person_with_ID_#1_prop } { ##1 } {
\ERROR Wert ~ für ~ '##1' ~ fehlt.
}
}
}
}
% Variablen und Befehle zum Einlesen von Schlüssel-Wert-Paaren
\tl_new:N \l_ionas_current_key_tl
\tl_new:N \l_ionas_current_value_tl
\cs_new:Npn \ionas_parse_key_value:w #1 = #2 \q_stop {
\tl_set:Nn \l_ionas_current_key_tl { #1 }
\tl_trim_spaces:N \l_ionas_current_key_tl
\tl_set:Nn \l_ionas_current_value_tl { #2 }
\tl_trim_spaces:N \l_ionas_current_value_tl
% K = \l_ionas_current_key_tl \\
% V = \l_ionas_current_value_tl \\
}
% Befehl zum Ausgeben aller Personen
\NewDocumentCommand { \getAllPersons } { } {
\begin{itemize}
\seq_map_inline:Nn \g_ionas_persons_seq {
\item
\getPersonInfo { ##1 } { given-name }
\c_space_tl
\getPersonInfo { ##1 } { name }
}
\end{itemize}
}
% Befehl zum Auslesen einer Bestimmten Eigenschaft
% - #1: ID
% - #2: Eigenschaft
\NewDocumentCommand { \getPersonInfo } { m m } {
\prop_item:cn { g_ionas_person_with_ID_#1_prop } { #2 }
}
\ExplSyntaxOff
\begin{document}
\minisec{Neue Personen anlegen}
(führt nicht zu einer Text-Ausgabe)
\newPerson{mmustermann}{
name = Mustermann,
given-name = Max,
number = 12345,
}
\newPerson{jdoe}{
name = Doe,
given-name = John,
number = 555123,
cuntry = USA,% Diese Angabe ist optional
}
\newPerson{jdoe2}{
name = Doe,
given-name = Jane,
number = 555321,
cuntry = USA,% Diese Angabe ist optional
}
% Das Folgende erzeugt einen Fehler, weil keine Nummer angeben ist
%\newPerson{ssorglos}{
% name = Sorglos,
% given-name = Susi,
%}
% Das Folgende erzeugt einen Fehler, weil die ID schon vergeben ist
%\newPerson{mmustermann}{
% name = Mustermann,
% given-name = Martin,
% number = 54321,
%}
\minisec{Alle Personen ausgeben}
\getAllPersons
\minisec{Bestimmte Infos abfragen}
Name: \getPersonInfo{mmustermann}{name}\\
Matrikelnummer: \getPersonInfo{jdoe}{number}
\end{document}[/code]
Für ausführliche Erklärungen fehlt mir grad die Zeit aber für einen Einstig in LaTeX3 schau gern mal in meinem Blog vorbei: http://tobiw.de/tbdm/funktionssymbole
Viele Grüße
Tobi