Top-Themen

AppleEntwicklungHardwareInternetLinuxMicrosoftMultimediaNetzwerkeOff TopicSicherheitSonstige SystemeVirtualisierungWeiterbildungZusammenarbeit

Aktuelle Themen

Administrator.de FeedbackApache ServerAppleAssemblerAudioAusbildungAuslandBackupBasicBatch & ShellBenchmarksBibliotheken & ToolkitsBlogsCloud-DiensteClusterCMSCPU, RAM, MainboardsCSSC und C++DatenbankenDatenschutzDebianDigitiales FernsehenDNSDrucker und ScannerDSL, VDSLE-BooksE-BusinessE-MailEntwicklungErkennung und -AbwehrExchange ServerFestplatten, SSD, RaidFirewallFlatratesGoogle AndroidGrafikGrafikkarten & MonitoreGroupwareHardwareHosting & HousingHTMLHumor (lol)Hyper-VIconsIDE & EditorenInformationsdiensteInstallationInstant MessagingInternetInternet DomäneniOSISDN & AnaloganschlüsseiTunesJavaJavaScriptKiXtartKVMLAN, WAN, WirelessLinuxLinux DesktopLinux NetzwerkLinux ToolsLinux UserverwaltungLizenzierungMac OS XMicrosoftMicrosoft OfficeMikroTik RouterOSMonitoringMultimediaMultimedia & ZubehörNetzwerkeNetzwerkgrundlagenNetzwerkmanagementNetzwerkprotokolleNotebook & ZubehörNovell NetwareOff TopicOpenOffice, LibreOfficeOutlook & MailPapierkorbPascal und DelphiPeripheriegerätePerlPHPPythonRechtliche FragenRedHat, CentOS, FedoraRouter & RoutingSambaSAN, NAS, DASSchriftartenSchulung & TrainingSEOServerServer-HardwareSicherheitSicherheits-ToolsSicherheitsgrundlagenSolarisSonstige SystemeSoziale NetzwerkeSpeicherkartenStudentenjobs & PraktikumSuche ProjektpartnerSuseSwitche und HubsTipps & TricksTK-Netze & GeräteUbuntuUMTS, EDGE & GPRSUtilitiesVB for ApplicationsVerschlüsselung & ZertifikateVideo & StreamingViren und TrojanerVirtualisierungVisual StudioVmwareVoice over IPWebbrowserWebentwicklungWeiterbildungWindows 7Windows 8Windows 10Windows InstallationWindows MobileWindows NetzwerkWindows ServerWindows SystemdateienWindows ToolsWindows UpdateWindows UserverwaltungWindows VistaWindows XPXenserverXMLZusammenarbeit

Suche nach mehreren Suchbegriffen in einer ASCII Datei, und wenn vorhanden eine Aktion ausführen

Frage Entwicklung Batch & Shell

Mitglied: shorty-xs

shorty-xs (Level 1) - Jetzt verbinden

12.11.2007, aktualisiert 20.11.2007, 3476 Aufrufe, 8 Kommentare

Hallo Ihrs,
ich hab ja schon viele wirklich gute Infos hier aus dem Forum gelesen, (Danke dafür) zu diesem Problem hab ich aber noch nichts gefunden.

Problem:

Ich habe eine ASCII Datei in der Artikelnummern in verschiedenen Reihenfolgen auftauchen, immer gefolgt von einer Zeile die die Anzahl dieser Komponente im Rechner. Ich möchte jetzt nach bestimmten Artiklenummern suchen um einen Test zu starten, wenn diese Artiklenummer vorhanden ist.

Beispiel ich suche ein Modem, das kann aber die ArtNr 1234 oder 3456 oder 0815 haben. Wenn ich eine dieser Artiklenummern finde, muß ich den Modemtest starten.

Mein Ansatz währe der, dass ich die möglichen Artiklenummer in einer Textdatei zusammen fasse, jede Nr. in einer eigenen Zeile, und oben drüber eine Sektion also:
01.
[Modem] 
02.
1234 
03.
3456 
04.
0815
Nenne wir sie mal artnr.txt

Dann kann ich alle Artikelmummern in einer Datei sammeln, weil das soll später für andere Komponenten auch noch kommen.

Jetzt möchte ich in der Stücklisten datei (serinummer.txt) die etwa so aussieht:
01.
5643 
02.
#1 
03.
0977 
04.
#1 
05.
5123 
06.
#2 
07.
1234 
08.
#1
möchte ich nun durchsuchen. Es könnte auch sein, dass die Artikelnummer merhmals vorhanden ist, dann muß ich 2 mal testen.

Das müsste ja mit einer verschachtelten for schleife gehen, aber mit welchen Parameter, ich hab ja schon einiges an Erfahrung mit batch aber die for paramter blicke ich immer noch nicht.

Ich habe schon folgende Artikel gelesen:
http://www.administrator.de/frage/wort-innerhalb-einer-textdatei-finden ...
http://www.administrator.de/Such-Assistent_starten_und_diesem_Parameter ...
http://www.administrator.de/Mittels_Batch-Datei_einen_Installationspfad ...


Gruß
Malte
Mitglied: bastla
16.11.2007 um 22:57 Uhr
Hallo shorty-xs und ein verspätetes Willkommen im Forum!

Für die Verarbeitung per Batch wäre eine "artnr.txt" in der Form
01.
Modem#1234#3456#0815#
vorzuziehen, da mit "findstr" dann nur die eine passende Zeile gefunden werden müsste - etwa so:
01.
@echo off & setlocal 
02.
set "SNr=D:\serinummer.txt" 
03.
set "ANr=D:\artnr.txt" 
04.
 
05.
for /f "delims=" %%i in ('findstr /v "#" "%SNr%"') do call :ProcessNumber "%%i" 
06.
goto :eof 
07.
 
08.
:ProcessNumber 
09.
set Typ= 
10.
for /f "delims=#" %%a in ('findstr "#%~1#" "%ANr%"') do set "Typ=%%a" 
11.
if not defined Typ goto :eof 
12.
 
13.
echo Starte den %Typ%-Test fuer %~1
Die "echo"-Zeile simuliert den Start des "Modem"-Tests.

Grüße
bastla
Bitte warten ..
Mitglied: shorty-xs
19.11.2007 um 08:42 Uhr
Hallo Bastla, vielen Dank!
Ich glaube das kann ich schon fast benutzen. Hab da aber noch ein paar Fragen, bzw. Änderungen.
Hallo shorty-xs und ein verspätetes
Willkommen im Forum!
Danke!

Für die Verarbeitung per Batch
wäre eine "artnr.txt" in der
Form vorzuziehen,
da mit "findstr" dann nur die eine
passende Zeile gefunden werden müsste -
etwa so:
01.
Modem#1234#3456#0815#
OK, das geht. Kann ich dann Artikelnummern für andere Komponeneten dort auch unterbringen? z.B. so:
01.
Modem#1234#3456#0815# 
02.
GSM#4356#9854# 
03.
COM3-4#2543#0981# 
04.
 
Das muß ich erstmal auseinander nehmen damit ich's verstehe:
01.
@echo off & setlocal 
02.
::set "SNr=D:\serinummer.txt" 
03.
set "SNr=.\%_sn%.txt" 
04.
set "ANr=D:\artnr.txt"
Soweit klar, echo ist schon vorher aus, setlocal begrenzt die Variablen auf diesen Bereich. Ich hab schon eine globale Variable %_sn%, ich glaube die kann ich dafür auch benutzen. Die ArtNr. txt würde ich glaube ich auch global anlegen, damit ich mehrfach drauf zugreifen kann. Ansonsten etwa so:
01.
for /f "delims=" %%i in ('findstr /v "#" ".\%_sn%.txt"') do call  :ProcessNumber "%%i" 
02.
goto :eof
Für was steht die Raute in der findstr Klammer? Wozu das goto :eof?
01.
  
02.
:ProcessNumber 
03.
set Typ= 
04.
for /f "delims=#" %%a in ('findstr "#%~1#" "%ANr%"') do set "Typ=%%a" 
05.
if not defined Typ goto :eof
Hier wird die Artikelnummern Zeile immer um ein feld verschoben. Damit nach Art.Nr jeder einmal gesucht wird. Ist glaube ich klar soweit.
Der Test start würde bei mir warschienlich so aussehen:
Die "echo"-Zeile
simuliert den Start des
"Modem"-Tests.

01.
if "%Typ%"=="Modem" ( 
02.
    echo Starte den %Typ%-Test fuer %~1 
03.
    call :Modemtest ) 
04.
if not defined Typ echo Kein Modem Installiert >>log.txt
Ich bin nicht so der Held mit Klammern, die if not defined Zeile im Testablauf kann man doch bestimmt durch ein else ersetzen, wo muß das hin? Mit in die Klammer ?
Grüße
bastla
Gruß, Malte
Bitte warten ..
Mitglied: bastla
19.11.2007 um 12:35 Uhr
Hallo Malte!

Kann ich dann Artikelnummern für andere Komponeneten dort auch unterbringen? z.B. so:
Modem#1234#3456#0815#
GSM#4356#9854#
COM3-4#2543#0981#
Das war eigentlich der Plan - "findstr" findet die Zeile mit der Artikelnummer, und mit "for" hole ich mir das erste Token (der hoffentlich einzigen, falls aber nicht, der letzten entsprechenden) Zeile.

for /f "delims=" %%i in ('findstr /v "#" ".\%_sn%.txt"') do call :ProcessNumber "%%i"
goto :eof
Für was steht die Raute in der findstr Klammer? Wozu das goto :eof?
Da ja nur die Nummern, aber nicht die Mengen, aus der Seriennummerndatei interessieren, filtere ich alle Zeilen, welche ein "#" enthalten, vorweg aus (noch genauer wäre ein zusätzliches "/b").

Mit "goto :eof" sorge ich dafür, dass nach dem Abarbeiten der gesamten Seriennummerndatei aber auch mal Schluss ist (und der Batch nicht nochmals in das ":ProcessNumber"-Unterprogramm läuft).

if "%Typ%"=="Modem" (
echo Starte den %Typ%-Test fuer %~1
call :Modemtest )
if not defined Typ echo Kein Modem Installiert >>log.txt
Ich bin nicht so der Held mit Klammern, die if not defined Zeile im Testablauf kann man doch bestimmt durch ein else ersetzen, wo muß das hin? Mit in die Klammer ?
Das "if not defined" prüft, ob (in der bereits ergänzten "ArtNr.txt") überhaupt ein Gerät gefunden wurde (da %Typ% ansonsten gar nicht existiert). Insofern wäre vor das "goto :eof" besser noch die Ausgabe einer entsprechenden Fehlermeldung zu setzen, etwa
01.
if not defined Typ echo Artikelnummer %~1 in der Datei ArtNr.txt nicht gefunden. >>log.txt & goto :eof
Die Fortsetzung würde ich dann vielleicht so gestalten:
01.
if exist "D:\Batch\%Typ%test.cmd" call "D:\Batch\%Typ%test.cmd" 
02.
... 
03.
...
In zB D:\Batch (natürlich auch besser per Variable angegeben) liegen dann eben die "Modemtest.cmd", "GSMtest.cmd", ... Damit sparst Du Dir die Abfragen der Art
01.
if "%Typ%"=="Modem" call "D:\Batch\Modemtest.cmd" 
02.
if "%Typ%"=="GSM" call "D:\Batch\GSMtest.cmd" 
03.
...
und könntest zusätzlich per Else auch noch einfach auf den Fall reagieren, dass zwar der Gerätetyp festgestellt werden konnte, aber die Testprogrammdatei dazu nicht vorhanden wäre.

Grüße
bastla
Bitte warten ..
Mitglied: shorty-xs
19.11.2007 um 13:05 Uhr
Erstmal vielen Dank Bastla!
Ich muß erstmal damit rumspielen. Mein Ziel ist zwar etwas anders, es könnte ja auch vor kommen, dass Modem und GSM drin sind, aber Du hast mir schonmal gewaltig weiter geholfen.

Ich würde also für jede Komponente die ich testen will nach dem vorhanden sein in der Stückliste suchen und dann testen, oder eben nicht.

Werde meine Ergebnisse natürlich hier posten!

P.S. mir fällt gerade ein, kann man das nicht anders rum aufziehen? Ich suche erstmal nach Modem in der ArtNr.txt und vergleiche dann die dahinter stehenden Nummern ob diese in der Stückliste %_sn%.txt sind?
Bitte warten ..
Mitglied: bastla
19.11.2007 um 15:22 Uhr
Hallo Malte!

P.S. mir fällt gerade ein, kann man das nicht anders rum aufziehen? Ich suche erstmal nach Modem in der ArtNr.txt und vergleiche dann die dahinter stehenden Nummern ob diese in der Stückliste %_sn%.txt sind?
Solange ich nicht genauer weiß, was Du überhaupt vorhast, kann ich nicht beurteilen, was vorteilhafter wäre - wenn Du nicht für alle Geräte Tests durchführen willst, kannst Du ja einfach nur nach den zu testenden Geräten suchen und zu diesem Zweck eine Eingabe der Art
01.
set /p "Ger=Welchen Geraetetyp testen?"
voschalten. Danach kannst Du dann über
01.
if /i "%Ger%"=="%Typ%" call "D:\Batch\%Typ%test.cmd"
gezielt den gewünschten Test aufrufen. Alternative, um mehrere Geräte angeben zu können:
01.
echo %Ger%|findstr /i "%Typ%" >nul && call "D:\Batch\%Typ%test.cmd"
wobei in %Ger% zB "Modem#COM3-4#COM7-8" eingegeben wurde.

Voraussetzung in beiden Fällen: Die Eingabe muss (bis auf die Groß-/Kleinschreibung) der Schreibweise in der "ArtNr.txt" entsprechen.

Grüße
bastla
Bitte warten ..
Mitglied: shorty-xs
19.11.2007 um 16:09 Uhr
Noch mals vielen Dank für Deine Hilfe,
ich hatte heute leider erst noch ein anderes Problem zu lösen, und konnte Dein Beispiel nicht testen. Ich vergesse manchmal, dass ich in Gedanken schon etwas weiter bin wie hier im forum Ich versuch es mal ohne Batch, einfach nur mit Text zu beschreiben.

Es geht darum das in einem Rechner verschiedenen Optionen vorhanden sein können.
Das kann Modem sein, das können aber auch 2 zusätzliche Serielle schnittstellen (COM3-4) sein oder eine W-LAN Karte, oder oder oder. Alles nur Beispiele-

Was drin ist, steht als Artikelnummern in der Stückliste. Diese wurde bisher nur für die unbeaufsichtigte Installation benutzt.

Wir haben ein Testscript, welches die benötigten Tests abruft. Im Moment muß der Tester dann selber auswählen ob die jeweilige Komponenten im Rechner ist oder nicht. Dies möchte ich um Zeit und Fehler zu sparen, gerne automatisieren.

Wenn also jetzt das Testscript an dem Punkt ankommt, an dem das Modem (falls vorhanden) getestet werden soll. Starte ich die Suche nach den möglichen Artikelnummern für das Modem. Wenn kein Modem drin ist, schreibe ich das so in's Protokoll.
An dem Punkt an dem wenn vorhanden COM3-4 getstet werden sollen, suche ich nach diesen möglichen Artiklenummern, um zu entscheiden Test JA/NEIN. usw.
Bitte warten ..
Mitglied: bastla
20.11.2007 um 00:03 Uhr
Hallo Malte!

Dann wird es tatsächlich sinnvoller sein, die Suche umzukehren - trotzdem würde ich bei der zeilenorientierten Struktur (wie oben dargestellt) der ArtNr.txt bleiben, allerdings nur Gerätetyp und Artikelnummern durch zB "=" (kann aber natürlich auch "#" bleiben) trennen und zwischen die Artikelnummern jeweils Leerstellen setzen, also
01.
Modem=1234 3456 0815 
02.
GSM=4356 9854 
03.
COM3-4=2543 0981
Der (ungetestete) "Test-Start-Batch" könnte dann so aussehen:
01.
@echo off & setlocal 
02.
set "TestDir=D:\Batch" 
03.
 
04.
echo Modem-Test 
05.
call :Check "Modem" 
06.
... 
07.
... 
08.
... 
09.
echo GSM-Test 
10.
call :Check "GSM" 
11.
... 
12.
... 
13.
echo Fertig. 
14.
goto :eof 
15.
 
16.
:Check 
17.
set Ger= 
18.
set ArtGer= 
19.
for /f "tokens=1* delims==" %%i in ('findstr /b /i "%~1" "%_an%.txt"') do ( 
20.
	set ArtGer=True 
21.
	for %%n in (%%j) do ( 
22.
		for /f "delims=" %%a in ('findstr /b "%%n" "%_sn%.txt"') do ( 
23.
			set Ger=True 
24.
			if exist "%TestDir%\%%itest.cmd" (call "%TestDir%\%%itest.cmd %%n") else echo %%itest.cmd nicht gefunden >>log.txt 
25.
26.
27.
28.
if not defined ArtGer echo %%i nicht in %_an%.txt gefunden >>log.txt & goto :eof 
29.
if not defined Ger echo Kein %%i installiert >>log.txt 
30.
goto :eof
Noch einige Hinweise zum Ablauf:

Die Verwendung des allgemeinen Unterprogrammes ":Check" (mit Übergabe des Gerätetyps als Parameter) setzt voraus, dass jedes Testprogramm von einem Batch mit dem Namen "%Typ%test.cmd" aufgerufen wird - es muss also "Modemtest.cmd", "GSMtest.cmd", "COM3-4test.cmd", etc geben. Wird ein entsprechender Batch nicht gefunden, erfolgt ein Eintrag im Protokoll "log.txt". Dem Testbatch wird (falls dort zB zu Dokuzwecken benötigt) die Artikelnummer des gefundenen Gerätes als Parameter %1 übergeben.

In der ersten "for"-Schleife wird jene Zeile, die mit dem Gerätetyp beginnt, in der Datei "ArtNr.txt" (dafür wurde, analog zur Variablen "%_sn%", "%_an%.txt" verwendet) gesucht und in die beiden Teile "Typbezeichnung" (%%i) und "Artikelnummern" (%%j) zerlegt. Wird keine entsprechende Zeile gefunden, so wird die Variable "ArtGer" nicht gesetzt, was am Ende des Unterprogramms zu einem entsprechenden Eintrag in die "log.txt" führt.

Die nächste Schleife geht alle Artikelnummern durch (ohne "/f", da die einzelnen Nummern ohnehin durch Leerstellen getrennt sind und daher einzeln erfasst werden können) und sucht jede einzelne Nummer (nur am Beginn jeder Zeile) in der Seriennummerndatei. Für jeden gefundenen Eintrag wird das Testprogramm aufgerufen - damit wäre sogar der Fall abgedeckt, dass die selbe Artikelnummer mehrmals in der Seriennummerndatei vorkäme.

Sobald auch nur eine Artikelnummer des überprüften Typs gefunden wurde, wird der Schalter "Ger" gesetzt - somit kann nach Durchlauf aller zum jeweiligen Typ gehörigen Artikelnummern anhand des Zustandes von "Ger" (vorhanden = "defined": Gerät gefunden; nicht vorhanden = "not defined": Gerät nicht gefunden) protokolliert werden, falls kein Artikel des zu testenden Gerätes in der Seriennummerndatei aufzufinden war.

Dass übrigens auch die "log.txt" über eine Variable angesprochen sowie am Beginn des Batches gelöscht werden sollte, sei nur erwähnt, ist aber noch nicht berücksichtigt.

Grüße
bastla
Bitte warten ..
Mitglied: shorty-xs
20.11.2007 um 08:09 Uhr
Wow, das isses.
Werde aber wohl heute auch noch nicht viel weiter kommen.

Melde mich so bald es was neues gibt.

Nochmals besten Dank.

Greetz
Malte
Bitte warten ..
Neuester Wissensbeitrag
Humor (lol)

Linkliste für Adventskalender

(3)

Information von nikoatit zum Thema Humor (lol) ...

Ähnliche Inhalte
Windows Tools
gelöst Powershell - Auswahl aus Listbox soll Aktion ausführen (4)

Frage von Schmierlappen zum Thema Windows Tools ...

Batch & Shell
gelöst Batch erst starten wenn bestimmte Datei vorhanden ist (7)

Frage von pdiddo zum Thema Batch & Shell ...

Heiß diskutierte Inhalte
Exchange Server
gelöst Exchange 2010 Berechtigungen wiederherstellen (20)

Frage von semperf1delis zum Thema Exchange Server ...

Windows Server
DHCP Server switchen (20)

Frage von M.Marz zum Thema Windows Server ...

Hardware
gelöst Negative Erfahrungen LAN-Karten (19)

Frage von MegaGiga zum Thema Hardware ...

Exchange Server
DNS Einstellung - zwei feste IPs für Mailserver (15)

Frage von ivan0s zum Thema Exchange Server ...