1. Dashboard
  2. Mitglieder
    1. Letzte Aktivitäten
    2. Benutzer online
    3. Team
    4. Mitgliedersuche
  3. Forenregeln
  4. Forum
    1. Unerledigte Themen
  • Anmelden
  • Registrieren
  • Suche
Alles
  • Alles
  • Artikel
  • Seiten
  • Forum
  • Erweiterte Suche
  1. AutoIt.de - Das deutschsprachige Forum.
  2. Mitglieder
  3. Yjuq

Beiträge von Yjuq

  • Self Modifying Code / IPC / Funktionen zur Laufzeit erzeugen

    • Yjuq
    • 10. Februar 2021 um 03:02

    So ganz werde ich nicht schlau. Je mehr ich darüber nachdenke welche Lösung die beste für dich ist umso mehr Fragen tauchen auf. Die wohl wichtigsten hier:

    Müssen es AutoIt Skripte sein? Kannst du nicht einfach Lua einbinden? Müssen diese Skripte independent laufen? Also eigenständige Programme? Oder nur reine Funktionssammlungen? Müssen unbedingt COM Objekte erstellt werden? Dürfen die eingebundenen Skripte uneingeschränkten Zugriff haben, oder sind da einige Beeinträchtigungen notwendig?

    Es gibt da einige Wege um das zu realisieren. Je nach Anforderung ist das eine besser geeignet als das andere. Aber es kommt wirklich sehr stark darauf an was genau gefordert ist. Kannst du mehr Informationen geben? Oder eine genauere Erläuterung über das System in welches es intigriert werden soll? Je mehr Informationen um so besser.

    Um ehrlich zu sein schreit das alles bisher nach Lua für mich.

  • Mein erstes AutoIT Projekt

    • Yjuq
    • 31. Januar 2021 um 05:20

    RIP - Da wurde dir ja was schönes aufgebrummt. x)

    Es sieht stark danach aus dass es sich dabei um eine Webapp handelt. Das könnte also etwas tricky werden für einen Anfänger :)

    Erst einmal: Moderne Webbrowser Automatisationen laufen über den Selenium WebDriver. Die "Mainstream" Browser unterstützen dies mit den neueren Versionen. Hier mal eine Liste aller relevanten Links um dir einen generellen Überblick zu erschaffen:

    https://en.wikipedia.org/wiki/Headless_browser

    https://www.autoitscript.com/forum/topic/19…rsion-01162021/

    https://developers.google.com/web/updates/20…headless-chrome

    https://developers.google.com/web/updates/20…arma-mocha-chai

    https://www.selenium.dev/documentation/en/webdriver/

    https://www.w3.org/TR/webdriver1/

    https://chromium.googlesource.com/chromium/src/+…river_status.md

    Well,... Das könnte wahrscheinlich mehr Fragen aufwerfen als es hilfreich ist...

    Hmn, ich würde vorschlagen du fragst erst mal deinen Chef ob es möglich ist den WebDriver für Goolge Chrome (ich schätze mal das wird der Browser sein der für die Webapp genutzt wird?) herunterladen und auf dem Rechner installieren kannst. Den Treiber findest du hier: https://chromedriver.chromium.org/downloads

    Wenn es möglich ist sag bescheid, dann können wir uns andere Methoden sparen und ich helfe dir dann in dieser Richtung weiter. Ansonsten müssen wir halt auf andere Mittel zugreifen...

    Sag mal, wie genau rufst du eigentlich die Anwendung auf? Öffnest du eine Internetseite oder ist da ein Icon auf dem Desktop? Ich möchte nur sichergehen dass es bei der Applikation auch wirklich um eine Webapp handelt. Versuch mal nen Rechsklick irgendwo zu machen und schau mal ob du da etwas hast wie "Quelltext ansehen" oder "Element untersuchen".

    Vielleicht ist das auch ein wenig Overkill für eine Anwendung die nur alle 90 Minuten was "anklicken" soll... Vielleicht hat ja noch jemand im Forum einen andere Vorschlag der genauso gut funktionieren würde. Ich würde halt Mausbewegungen vermeiden wollen. :P

  • Raspberry Pi AutoIT

    • Yjuq
    • 28. Januar 2021 um 09:46

    Windows 10 IoT läuft auf dem Raspberry Pi 2 & 3. Ob da allerdings dann auch AutoIt drauf läuft, keine Ahnung. Ich vermute aber mal eher weniger da dir schlichtweg alles aus der WinAPI fehlt bis aus einige Core Funktionen. Vielleicht hast du auch Glück mit Wine unter Linux. Aber wieso AutoIt? Python ist die gängiste Sprache in der Linux Welt für Scripting.

  • Mein erstes AutoIT Projekt

    • Yjuq
    • 26. Januar 2021 um 03:52

    Nicolai

    Ich kann dir einen Grundlagen Crashkurs geben. Ich habe momentan ziemlich viel Zeit und nicht viel zu tun.

    Automatisierungen von Webbrowsern mit AutoIt ist dann auch etwas schwieriger. Eigentlich fehlt uns sowieso noch eine Menge an Informationen um dir überhaupt effektiv helfen zu können. Darfst du Screenshots von der Software hochladen? Wenn es sich wirklich um eine Webapp handelt dann sitzt du da als Anfänger noch in 3 Monaten dran. :P

    Am besten wäre es mal wen in der IT Firma zu fragen (der sich auch mit AutoIt auskennt) dass er dir alle notwenigen Informationen zukommen lässt um das auch zu automatisieren oder ggf. um Hilfestellung im Internet zu erfragen.

  • Mein erstes AutoIT Projekt

    • Yjuq
    • 22. Januar 2021 um 10:56

    Handelt es sich dabei um eine Applikation welche im Webbrowser aufgerufen wird? Ansonsten kannst du mir dem AutoIt Info Tool die entsprechenden Control ID's auslesen und diese via Control ControlClick einfach ansprechen. Packst noch ein paar If-Abfragen mit rein, ne hübsche Schleife und nen Timer der alle 90 Minuten triggert. Fertig :P

    Das ist zumindest die Quick & Dirty Variante. Die kannst du allerdings um einiges verbessern. Du hattest im anderen Thread erwähnt dass du "nicht viel mit Programmierung zu tun" hattest? Am einfachsten ist es erst mal bei deinem Rechner einfach den Windows Calculator aufzurufen und zu versuchen einzelne Buttons dort anzuklicken.

    Du hast per TeamViewer den Zugriff auf den Zielrechner, korrekt? Ist dort AutoIt drauf installiert oder kannst du zumindest das Info Tool darauf aufrufen? Ansonsten kommst du ja noch nicht mal an die Control ID's dran.

    Ich werde dir bei deiner Aufgabe helfen. Allerdings gebe ich dir nur soweit Hilfestellung sodass du die Dinge selber lösen kannst. Alles andere wäre für ein Praktikum für dein Chef vermutlich inakzeptabel. Hast du für die Aufgabe eine Deadline? | Nvm, die Frage hattest du mir schon beantwortet.

  • [Erledigt] > AMD Radeon R 290 < oder ähnliche GPU

    • Yjuq
    • 22. Januar 2021 um 08:32
    Zitat von Musashi

    Ob das Teil leistungsmäßig deinen Ansprüchen genügt, musst du beurteilen.

    Primäres Ziel ist es sowieso erst mal wieder an meine Daten ran zu kommen. In 3~4 Monaten schaffe ich mir sowieso komplett neue Hardware ran. Meine Kartoffel ist nun über 10 Jahre alt und davon ist kaum was zu verwerten. :') - Leider fehlt mir noch ein wenig Geld um alle Teile zu bestellen. Da mir aber nun meine GPU abgeraucht ist muss für's erste eine Ersatzlösung ran.

    Ich schicke dir eine PM bezüglich meiner Adresse. Ich bedanke mich schon mal im Vorraus.

  • [Erledigt] > AMD Radeon R 290 < oder ähnliche GPU

    • Yjuq
    • 22. Januar 2021 um 01:34

    Servus o/
    Mir ist bei meinen (ziemlich alten) PC meine GPU drauf gegangen. Ich habe dort noch eine Radeon R 290 verbaut. Ich suche momentan nach einer GPU mit ähnlicher Leistung. Kann von mir aus gebraucht sein. Leider habe ich keine Onboard Grafikkarte (oder zweiten Rechner) weshalb ich noch nicht mal auf meine wichtigen Daten zugreifen kann. Falls jemand noch ne GPU im Keller hat die noch funktioniert würde ich sie für einen angemessenen Preis kaufen. Prinzipiell traue ich dem Forum hier schlichtweg mehr als die Angebote auf ebay. ^^

    LG Yjuq

  • Neu hier und in der IT

    • Yjuq
    • 22. Januar 2021 um 01:28

    Huh - Keine Programmiererfahrung aber dein Chef lässt dich direkt an soetwas Schwieriges für einen kompletten Anfänger ran? Hast du deafür eine zeitliches Limit? Wie lange ist das Praktikum denn?

    Herzlich Willkommen o/

  • Kratzer an Hintertür, was tun?

    • Yjuq
    • 15. Dezember 2020 um 15:40

    Hi, wir sind ein Programmierforum für die Programmiersprache AutoIt. Wir haben erst mal prinzipiell nichts mit Autos am Hut. Aber vielleicht bekommst du dennoch eine hilfreiche Antwort von jemanden. Lediglich als kleine Info für den Fall dass dir garkeiner antworten sollte.

    LG. Yjuq

  • Unter-Schleife per Knopfdruck beenden

    • Yjuq
    • 26. November 2020 um 05:42

    Naja, das ist auch ganz simpel. Im prinzip werden die neuen Events gefetcht nachdem du GuiGetMsg() aufrufst. Demnach musst du es nur aufrufen und auf Events reagieren:

    AutoIt
    #include <GUIConstantsEx.au3>
    #include <MsgBoxConstants.au3>
    
    Local $hMainGUI = GUICreate("Hallo Welt", 310, 100)
    GUICtrlCreateLabel("Klicke auf OK und dann auf den Close- oder Cancel-Button." & @CRLF _
      & "Schleife wird NICHT beendet, GUI wird NICHT geschlossen!", 10, 10, -1, 50)
    Local $iOKButton = GUICtrlCreateButton("OK", 80, 70, 60)
    Local $iCancelBtn = GUICtrlCreateButton("Cancel", 160, 70, 60)
    GUISetState(@SW_SHOW, $hMainGUI)
    
    Global $g_bCancel = False
    Global $bOK = False
    
    While 1
      ConsoleWrite("$g_bCancel (MainLoop): " & $g_bCancel & @CRLF)
      If $bOK Then
        $bOK = False
        TestFunc1()
      EndIf
    
        events()
    WEnd
    
    Func TestFunc1()
      Local $iCnt = 0
      Do
        Sleep(250)
        ConsoleWrite("$g_bCancel: " & $g_bCancel & @CRLF)
        If $g_bCancel Then
          $g_bCancel = False
          ExitLoop
        EndIf
    
        GUICtrlSetData($iOKButton, $iCnt)
        $iCnt += 1
        events()
      Until $iCnt = 40 ; Läuft ca. 10 Sekunden.
    EndFunc   ;==>TestFunc1
    
    Func events()
          Switch GUIGetMsg()
        Case $GUI_EVENT_CLOSE
          Exit
    
        Case $iOKButton
          $bOK = True
          ConsoleWrite("$g_bCancel (Ende): " & $g_bCancel & @CRLF)
    
        Case $iCancelBtn
          $g_bCancel = True
    
      EndSwitch
    EndFunc
    Alles anzeigen

    Sleep() verhindert aber das sofortige schließen. Ist genauso ein Fall den du nicht in Events setzen möchtest. Hier mal eine Variation mit einen richtigen Timer:

    AutoIt
    #include <GUIConstantsEx.au3>
    #include <MsgBoxConstants.au3>
    
    Local $hMainGUI = GUICreate("Hallo Welt", 310, 100)
    GUICtrlCreateLabel("Klicke auf OK und dann auf den Close- oder Cancel-Button." & @CRLF _
      & "Schleife wird NICHT beendet, GUI wird NICHT geschlossen!", 10, 10, -1, 50)
    Local $iOKButton = GUICtrlCreateButton("OK", 80, 70, 60)
    Local $iCancelBtn = GUICtrlCreateButton("Cancel", 160, 70, 60)
    GUISetState(@SW_SHOW, $hMainGUI)
    
    Global $g_bCancel = False
    Global $bOK = False
    
    While 1
      ConsoleWrite("$g_bCancel (MainLoop): " & $g_bCancel & @CRLF)
      If $bOK Then
        $bOK = False
        TestFunc1()
      EndIf
    
        events()
    WEnd
    
    Func TestFunc1()
        Local $iCnt = 0
        Local $timer = TimerInit()
      Do
        If TimerDiff($timer) > 250 Then
            ConsoleWrite("$g_bCancel: " & $g_bCancel & @CRLF)
            If $g_bCancel Then
            $g_bCancel = False
            ExitLoop
            EndIf
    
            GUICtrlSetData($iOKButton, $iCnt)
            $iCnt += 1
            $timer = TimerInit()
        EndIf
        events()
      Until $iCnt = 40 ; Läuft ca. 10 Sekunden.
    EndFunc   ;==>TestFunc1
    
    Func events()
          Switch GUIGetMsg()
        Case $GUI_EVENT_CLOSE
          Exit
    
        Case $iOKButton
          $bOK = True
          ConsoleWrite("$g_bCancel (Ende): " & $g_bCancel & @CRLF)
    
        Case $iCancelBtn
          $g_bCancel = True
    
      EndSwitch
    EndFunc
    Alles anzeigen

    Solche Sachen lassen sich aber mit einer "Manager" Funktion, welche AutoIt Skript von dem Windows Events trennt, ziemlich einfach lösen.

  • Unter-Schleife per Knopfdruck beenden

    • Yjuq
    • 25. November 2020 um 23:32

    Du solltest in Windows Events prinzipiell keine Schleifen verwenden. Das sorgt nur dafür dass sich das Programm aufhängt und Events nicht mehr richtig funktionieren.

    Stattdessen kannst du eine Variable in dem Event setzen um dann deine gewünschte Funktion aufzurufen:

    AutoIt
    #include <GUIConstantsEx.au3>
    #include <MsgBoxConstants.au3>
    
    Opt("GUIOnEventMode", 1) ; Wechsle in den OnEvent Modus
    
    Local $hMainGUI = GUICreate("Hallo Welt", 300, 100)
    GUISetOnEvent($GUI_EVENT_CLOSE, "CLOSEButton")
    GUICtrlCreateLabel("Klicke auf OK und dann auf den Close-Button." & @CRLF _
      & "GUI wird NICHT geschlossen!", 30, 10, -1, 50)
    Local $iOKButton = GUICtrlCreateButton("OK", 120, 70, 60)
    GUICtrlSetOnEvent($iOKButton, "OKButton")
    GUISetState(@SW_SHOW, $hMainGUI)
    
    Global $g_bCancel = False
    Global $bOK = False
    
    While 1
      Sleep(100) ; Im Leerlauf bummeln
      ConsoleWrite("$g_bCancel (MainLoop): " & $g_bCancel & @CRLF)
      If $bOK Then
          TestFunc1()
          $bOK = False
      EndIf
    WEnd
    
    Func OKButton()
      ; Beachte: an diesem Punkt w&auml;re @GUI_CtrlId gleich $iOKButton,
      ; und @GUI_WinHandle w&auml;re gleich $hMainGUI
    ;   MsgBox($MB_OK, "GUI Event", "Du hast auf OK geklickt!")
        If $bOK = True Then $g_bCancel = True
      $bOK = True
    EndFunc   ;==>OKButton
    
    Func CLOSEButton()
      ; Beachte: an diesem Punkt w&auml;re @GUI_CtrlId gleich $GUI_EVENT_CLOSE,
      ; und @GUI_WinHandle w&auml;re gleich $hMainGUI
    ;   MsgBox($MB_OK, "GUI Event", "Du hast auf CLOSE geklickt! Programm wird beendet...")
      $g_bCancel = True
      Exit
    EndFunc   ;==>CLOSEButton
    
    Func TestFunc1()
      Local $iCnt = 0
      Do
        Sleep(250)
        ConsoleWrite("$g_bCancel: " & $g_bCancel & @CRLF)
        If $g_bCancel Then Exit
    
        GUICtrlSetData($iOKButton, $iCnt)
        $iCnt += 1
      Until $iCnt = 40 ; Läuft ca. 10 Sekunden.
    EndFunc   ;==>TestFunc1
    Alles anzeigen

    Noch schöner (und bei einer größeren GUI) ist natürlich eine Funktion die das managed.

  • Warum funktioniert GetPixelColor nicht???

    • Yjuq
    • 9. November 2020 um 20:11

    Wenn du Probleme mit Deutsch hast: Ich bin auch der englischen Sprache mächtig, falls das für dich angenehmer ist. Du darfst mir auch gerne private Nachrichten über das Forum schreiben. Ich antworte sobald ich diese sehe. Bin aber eher einer der mehr inaktiven Mitglieder hier. Ich brauch AutoIt nicht mehr so häufig wie ich es mal gebraucht hatte.

  • Warum funktioniert GetPixelColor nicht???

    • Yjuq
    • 9. November 2020 um 20:07

    Den Kommentar zu der "Spieleautomation" oder wie du es nanntest "Spielautomaten" bezieht sich auf Programme, welche darauf abziehlen Computerspiele zu automatisieren. Dies widerspricht den Forenregeln und wird hier nicht geduldet. Das hat nichts mit einem Casino zu tun. ^^

    Die Dokumentationen sind manchmal schwer zu verstehen wenn man den Sinn hinter einigen Sachen nicht kennt oder Vergleichsbeispiele hat. Weißt du was über Elektrotechnik und wie Logic-Gates funktionieren? Diese Bit-Funktionen machen genau das Selbe, lediglich mit mehreren "Signalen" gleichzeitig. Du kannst dich ja mal ein wenig hier durchwühlen: Logic Gates

    Es gab da auch eine gute Deutsche Seite über Elektrotechnik. Aber mir fällt der Name nicht mehr ein... Sorry

  • Warum funktioniert GetPixelColor nicht???

    • Yjuq
    • 9. November 2020 um 19:52

    @Musashi - Ich denke eine vorgefertigte Lösung zu präsentieren hilft nicht wirklich. Ich bleibe mal bei meiner Vorrangehensweise und erkläre ihm lieber wo seine Fehler sind. Alles andere macht für mich keinen Sinn.

    dask - Deine Antworten sind zumindest schon einmal nicht schlecht. Ich habe dir die Fragen gestellt um selber erst mal zu sehen ob du auch selber verstehst was du da gepostet hast. Prinzipiell scheinst du ja schon mal gewisse Grundlogik und ein allgemeines Verständnis von Progammabläufen zu haben. Sprich: Geordnete Gedankengänge von "Was will ich erreichen?" zu "Wie setze ich das um?". Das ist schon einmal eine gute Vorraussetzung. Nun zu deinen Fehlern die du mit dem Skript gepostet hast.

    Frage 1:

    Das ist soweit korrekt. Diese Zeile macht auch genau das, was du beschrieben hast.

    Frage 2:

    Das ist prinzipiell auch korrekt. Zumindest wenn es um die Logik dahinter geht. Jedoch ist das nicht korrekt umgesetzt. In der Programmierung existieren Strings. Strings sind auf gut Deutsch eigenlich nur Zeichenketten. In AutoIt werden Strings üblicherweise in " oder ' Zeichen verpackt. Was du tatsächlich abfragst ist Folgendes: Ist $iColor nicht gleich der Zeichenkette "Hex(C9C9C7)"? Du fragst hier nach der Zeichenkette ab, nicht nach dem Hexwert C9C9C7. Das ist schon ein Fehler. Was du eigentlich machen möchtest ist das hier: $iColor <> 0xc9c9c7

    Um einen Hexdezimalen Wert in AutoIt darzustellen, kannst du einfach 0x vorne heran fügen. Die Funktion Hex() gibt dir den Hexdezimalen Wert einer Dezimalzahl zurück. Konvertiert also von Dezimalsystem zu Hexdezimalsystem. Der Rückgabewert ist allerdings ebenfalls ein String. AutoIt ist sehr freundlich was Datentypen angeht, meistens jedenfalls. Bedeutet dass "123" und 123 für AutoIt in Vergleichen das Selbe ist.

    Hex() - Dokumentation

    Frage 3:

    Das Grundprinzip von Schleifen scheinst du zu kennen. Die Formulierung ist etwas üppig und nicht wirklich korrekt, aber ich sehe was du damit ausdrücken möchtest. Vom Sinn her ist das richtig.

    ---

    Nun kommt der Knackpunkt in deinem Skript. Du fragst lediglich einmalig ab, welche Farbe an der Koordinate (738 | 822) befindet. Diese Farbe wird in $iColor gespeichert. Danach überprüfst du ob sich $iColor irgendwann einmal verändert. Das Problem ist allerdings, du fragst niemals nochmal nach der Farbe an besagter Koordinate. Heißt, dein $iColor bleibt immer gleich und deine Abfrage in der While-Schleife gibt demnach immer das Selbe Ergebnis zurück. Um das zu umgehen musst du $iColor in der While-Schleife aktuallisieren.

    ---

    Andy - Tja, da warst du mal wieder schneller... x)

  • Warum funktioniert GetPixelColor nicht???

    • Yjuq
    • 9. November 2020 um 08:16

    Hi o/
    Willkommen im Forum!

    Dein Code funktioniert nicht weil es einige Fehler beinhaltet. Wir geben hier normalerweise Hilfe zur Selbsthilfe, das bedeutet du bekommst (zumindest von mir) die grobe Richtung vorgegeben. Den Rest must du dir aber selber erschließen.

    Da es dir wahrscheinlich an Grundlagen mangelt, fangen wir doch einfach mal mit einem einfachen Fragespiel an:

    Was macht Local $iColor = Hex(PixelGetColor(738,822,1),6)?

    Was macht While $iColor <> "Hex(C9C9C7)"?

    Was ist eine While-Schleife?

    Und zu letzt: Was möchtest du eigentlich erreichen?

  • Yjuq's File Format - *.yff

    • Yjuq
    • 17. August 2020 um 21:23
    Zitat von AspirinJunkie

    Kannst du das genauer erläutern?

    Ich meine damit dass es keinen generellen Parser gibt den du für jede Programmiersprache einfach nutzen kannst. Einen JSON Parser in Form einer DLL zum Beispiel. Stattdessen hat jede Programmiersprache eine eigene Implementation dafür.

    https://www.json.org/json-en.html

    Scroll mal runter auf der Seite, da fängt es schon an. Sagen wir mal, ich hab jetzt eine Programmiersprache die keinen JSON Parser von sich aus hat, viel spaß den Parser zu schreiben.

  • Yjuq's File Format - *.yff

    • Yjuq
    • 17. August 2020 um 15:42
    Zitat von BugFix

    Ich hatte keineswegs die Absicht, dein Werk madig zu machen

    Huh, davon bin ich auch nicht ausgegangen. Text im Internet ist sowieso immer schwierig zu interpretieren wenn es um die momentane emotionslage des Author geht. ^^

    Hauptsächlich sollte mein Beispiel demonstrieren wie das Dateiformat funktioniert, nicht welche Vorteile es gegenüber anderen bietet und welche Nachteile. Darum geht es auch gar nicht. Das ist nur entstanden da ich einen spezifischen Anwendungsfall hatte wo vorhandene Dateiformate schlichtweg versagen oder es eben kein Parser dafür existiert für meine genutzte Programmiersprache. Beispiel JSON - Es gibt zwar zig implementationen, diese sind aber alle Programmiersprachen spezifisch.

    Welp, es musste was her was extrem einfach zu parsen ist. Letzten endes ist das ganze gestern Nacht in einer halben Stunde entstanden. xD

  • Yjuq's File Format - *.yff

    • Yjuq
    • 17. August 2020 um 13:20
    Zitat von BugFix

    Vielleicht solltest du mal eine Bsp. generieren, dass die erforderliche Flexibilität beinhaltet. Das hier gezeigte Bsp. ist (deutlich einfacher lesbar) auch in einer INI abbildbar.

    Verstehe dein Einwand nicht. Die INI Datei zwingt dich in folgendes Format:

    [Section]

    Key=Value

    Kommentare müssen mit einen ; am Zeilenanfang beginnen

    Zumal es auch nicht möglich ist folgendes zu machen:

    [Section]

    Key==Value

    Wie kann ich den Key jetzt "Key=" nennen und den Value auf "Value" setzen?

    Kurz, die INI und dazugehörigen AutoIt Funktionen schränken dich ein. Mein Format soll eben das Problem umgehen. Es geht hauptsächlich darum die Einschränkungen, wie die Datensätze in der Datei hinterlegt werden müssen, lockerer zu gestalten. Ich hab meine Gründe dazu und auch sogar ein Anwendungsfall wo die INI schlichtweg versagt. Ich dachte ich teile meine Gedanken dazu weil ein Parser für diese Variante schnell geschrieben ist.

  • Yjuq's File Format - *.yff

    • Yjuq
    • 16. August 2020 um 23:34

    Hallo o/

    Aus verschiedenen Gründen brauchte ich ein Dateiformat, welches Hauptsächlich Konfigurationen speichert. Mein erster Gedanke war logischerweise eine simple *.ini Datei. Jedoch war das Format leider noch viel zu unflexibel für mein Vorhaben. Andere Dateiformate waren und sind auch viel zu kompliziert (z.B. JSON) um schnell mal einen Parser dafür zu schreiben. Also hatte ich mir überlegt, wie kann man ein Dateiformat so simpel wie möglich halten und dennoch sämtliche Möglichkeiten offen halten?

    Lustigerweise hatte ich dann auch eine Idee. Der Parser dazu war auch schnell geschrieben (obwohl dieser sicherlich mit String Funktionen um einiges schneller wäre). Ich nenne das Format Yjuq's File Format oder kurz: YFF - *.yff

    Das Prinzip dieses Formates ist extrem simpel. Du wählst dir dein Delimeter und Escape Zeichen aus. Man kann sich auch mehrere aussuchen. Zu einfachen Demonstationszwecken benutze ich folgende:

    Delimeter: < und >

    Escape: \

    Alles was zwischen den Delimeter ist wird als Datensatz gewertet, alles was direkt nach einem Escape Zeichen in einem Datensatz kommt, wird ebenfalls als Datensatz gewertet. Das bedeutet dass die Escape Zeichen hauptsächlich dazu dienen, ebenfalls die Delimeter als Datensatz zu erkennen. Logischerweise kannst du damit auch Escape Zeichen als Datensatz werten lassen. Alles andere, was nicht zwischen Delimeter steht, wird schlichtweg ignoriert.

    Dieses Dateiformat erlaubt es das Dateiformat frei zu bestimmen und dennoch die Datensätze zu deklarieren. Die ignorierten Zeichen können als Kommentare genutzt werden oder für weitere Datensätze für andere Delimeter und Escape Einstellungen. Da bleibt es eurer Fantasie überlassen.

    Code: example.yff
    --------------------------------------------------------------------------------
    
    Das ist ein Beispiel für ein valides Dokument. Da alle Zeichen bis auf die
    Zeichen zwischen [Delimeter] ignoriert werden, kann ich hier schlichtweg den
    Platz für Dokumentationszwecke nutzen.
    
    --------------------------------------------------------------------------------
    
    Hier ein Beispiel für ein Datensatz: <Ich bin ein Datensatz>
    
    Da "Ich bin ein Datensatz" zwischen 2 Delimeter geschrieben wurde, wird dies als
    gültiger Datensatz erkannt.
    
    --------------------------------------------------------------------------------
    
    Hier ein weiteres Beispiel: <\<Daten\>>
    
    Dies würde euch den Datensatz "<Daten>" ausgeben.
                                    ^^^^^
                          Da dies nicht escaped wurde, ist das auch ein Datensatz ^^
    
    --------------------------------------------------------------------------------
    
    In:     <data<
    Out:    "data"
    
    In:     >data>
    Out:    "data"
    
    In:     <da\ta>
    Out:    "data"
    
    In:     <da\\ta>
    Out:    "da\ta"
    
    --------------------------------------------------------------------------------
    
    Ich denke das Prinzip ist klar.
    Alles anzeigen

    Hier einmal ein Beispielskript mit dem Parser dazu:

    AutoIt
    #include <Array.au3>
    
    Local $string = FileRead("example.yff")
    Local $array = yffParse($string)
    
    _ArrayDisplay($array)
    
    ; $string     -> Der zu parsende String
    ; $del        -> Array im folgenden Format:
    ;                > [0] = Anzahl der Delimeter Zeichen
    ;                > [1] = Asc(Delimeter 1)
    ;                > [2] = Asc(Delimeter 2)
    ;                > [x] = Asc(Delimeter x)
    ; $esc        -> Array im folgenden Format:
    ;                > [0] = Anzahl der Escape Zeichen
    ;                > [1] = Asc(Escape 1)
    ;                > [2] = Asc(Escape 2)
    ;                > [x] = Asc(Escape x)
    Func ycfParse($string, $del = Default, $esc = Default)
        If $del = Default Then
            Dim $del[3]
            $del[0] = 2
            $del[1] = Asc("<")
            $del[2] = Asc(">")
        EndIf
    
        If $esc = Default Then
            Dim $esc[2]
            $esc[0] = 1
            $esc[1] = Asc("\")
        EndIf
    
        Local $str = StringToASCIIArray($string, 0, StringLen($string), 1)
        Local $dat[2] = [1]
        Local $mod, $flg
    
        For $i = 0 To UBound($str) - 1
            Switch $mod
    
                ; searching for delimeter or escape
                Case 0
    
                    ; check for delimeter
                    If yffCheck($str[$i], $del) Then $mod = 1
    
                    ; check for escape
                    If yffCheck($str[$i], $esc) Then $mod = 2
    
                ; getting the data
                Case 1
    
                    ; check for delimeter
                    If Not $flg And yffCheck($str[$i], $del) Then
                        $mod = 0
    
                        ; check for array size
                        $dat[0] += 1
                        If $dat[0] = UBound($dat) Then ReDim $dat[($dat[0]) * 2]
                    Else
    
                        ; check for escape
                        If Not $flg And yffCheck($str[$i], $esc) Then
                            $flg = True
                        Else
                            $dat[$dat[0]] &= Chr($str[$i])
                            $flg = False
                        EndIf
                    EndIf
    
                ; skip one
                Case 2
                    $mod = 0
                    $flg = False
            EndSwitch
        Next
    
        ; crop array
        ReDim $dat[$dat[0]]
        $dat[0] -= 1
    
        Return $dat
    EndFunc
    
    Func yffCheck($char, $sym)
        For $i = 1 To $sym[0]
            If $char = $sym[$i] Then Return True
        Next
    EndFunc
    Alles anzeigen

    Der Parser selber schmeißt euch einfach eine Liste mit allen Datensätzen zu. Im Index 0 ist immer die Anzahl der Datensätze im Array. Wie Ihr die Datensätze interpretiert bleibt euch überlassen. Hier mal ein einfaches Beispiel um Daten im Key = Value Format zu speichern:

    Code: example.yff
    --------------------------------------------------------------------------------
    
    Die "=" Zeichen im Dokument dienen nur für die Lesbarkeit des Menschen. Sie
    haben für den Parser absolut keine Bedeutung da diese außerhalb der Delimeter
    liegen. Sie werden also schlichtweg ignoriert...
    
    --------------------------------------------------------------------------------
    
    <Key 1> = <Value 1>
    <Key 2> = <Value 2>
    
    <Key 3>        Kommentar zu "Key 3"
    <Value 3>      Kommentar zu "Value 3"
    
    --------------------------------------------------------------------------------
    Alles anzeigen

    Und hier das Skript:

    AutoIt
    #include <Array.au3>
    
    Local $string = FileRead("example.yff")
    Local $array = yffParse($string)
    Local $keyvalue[$array[0] / 2][2]
    
    ; Map 1D Array to 2D Array | Key=Value Format
    For $i = 1 To $array[0] / 2
        $keyvalue[$i - 1][0] = $array[$i * 2 - 1]
        $keyvalue[$i - 1][1] = $array[$i * 2]
    Next
    
    _ArrayDisplay($keyvalue)
    
    Func yffParse($string, $del = Default, $esc = Default)
        If $del = Default Then
            Dim $del[3]
            $del[0] = 2
            $del[1] = Asc("<")
            $del[2] = Asc(">")
        EndIf
    
        If $esc = Default Then
            Dim $esc[2]
            $esc[0] = 1
            $esc[1] = Asc("\")
        EndIf
    
        Local $str = StringToASCIIArray($string, 0, StringLen($string), 1)
        Local $dat[2] = [1]
        Local $mod, $flg
    
        For $i = 0 To UBound($str) - 1
            Switch $mod
    
                ; searching for delimeter or escape
                Case 0
    
                    ; check for delimeter
                    If yffCheck($str[$i], $del) Then $mod = 1
    
                    ; check for escape
                    If yffCheck($str[$i], $esc) Then $mod = 2
    
                ; getting the data
                Case 1
    
                    ; check for delimeter
                    If Not $flg And yffCheck($str[$i], $del) Then
                        $mod = 0
    
                        ; check for array size
                        $dat[0] += 1
                        If $dat[0] = UBound($dat) Then ReDim $dat[($dat[0]) * 2]
                    Else
    
                        ; check for escape
                        If Not $flg And yffCheck($str[$i], $esc) Then
                            $flg = True
                        Else
                            $dat[$dat[0]] &= Chr($str[$i])
                            $flg = False
                        EndIf
                    EndIf
    
                ; skip one
                Case 2
                    $mod = 0
                    $flg = False
            EndSwitch
        Next
    
        ; crop array
        ReDim $dat[$dat[0]]
        $dat[0] -= 1
    
        Return $dat
    EndFunc
    
    Func yffCheck($char, $sym)
        For $i = 1 To $sym[0]
            If $char = $sym[$i] Then Return True
        Next
    EndFunc
    Alles anzeigen

    Nun denn, für meine Zwecke jedenfalls nutzbar. Ich dachte ich teile das mit euch. Wer einen besseren Parser schreiben möchte, nur zu. Ich hantiere mit eine kleine Menge an Daten dh. reicht mir die Geschwindigkeit aus. Jedoch würde ich mich natürlich über ein free update freuen. :P

    Hauptsächtlich geht es bei dem Post darum eine einfache Möglichkeit zu haben Datensätze in menschenlesbarer Form zu speichern und abzurufen. Dabei sollte das Format nicht kompliziert sein aber funktionsreich genug um auch Datensätze zu erzeugen die via Software dann richtig aufbereitet werden können. Eine einfache Array Liste reicht da meiner Ansicht nach aus. Darauf lassen sich weitere Filter und Bedingungen anknüpfen um das Dateiformat zu extenden. Sprich: Datensätze weiter auswerten und entsprechend so zu kategorisieren wie gewünscht.

  • Wie FileIconInit aufrufen?

    • Yjuq
    • 2. August 2020 um 15:32

    Hi, ich hab keine Ahnung von Nim aber von das bisschen was ich mir gerade zusammengesucht habe würde ich einfach aus der WinAPI die 3 klassischen Funktionen LoadLibraryA, GetProcAddress und FreeLibrary nutzen. In GetProcAdress kannst du nämlich die Ordnungszahl benutzen.

    https://rosettacode.org/wiki/Call_a_fu…g_with_Nim_code

    Vielleicht hilft das ja.

Spenden

Jeder Euro hilft uns, Euch zu helfen.

Download

AutoIt Tutorial
AutoIt Buch
Onlinehilfe
AutoIt Entwickler
  1. Datenschutzerklärung
  2. Impressum
  3. Shoutbox-Archiv
Community-Software: WoltLab Suite™