2012-12-14 39 views
1

你好,我正在研究一個小腳本,它允許我解析輸入信息。這是行得通的,但我知道有一個更好的方法來做到這一點。請,我正在努力學習[自學],所以撕開了我。輸入將是如下:清理TCL列表並輸出

C7-0-4-U1 36.5 mHz IN7-0-4-0 567 mHz 00:15:d0:e3:b0:41 online(pt) 10.106.156.129 42.0 -0.5 35.1 -3.0 38.7 0.0E+000 0.0E+000 9 0 12:20:32 AM rZ5 1  


C7-0-4-U1 36.5 mHz IN7-0-4-0 567 mHz 2c:9e:5f:de:ed:36 w-online(pt) 10.113.52.11 36.5 0.0 35.1 -5.0 37.7 4.9E-006 0.0E+000 9 0 12:20:32 AM r4G 0  


C7-0-4-U1 36.5 mHz IN7-0-4-0 567 mHz e4:83:99:6d:57:ad w-online(pt) 10.113.45.239 43.5 0.0 35.1 -4.6 39.5 5.8E-006 0.0E+000 8 0 12:20:34 AM r4G 0  


C7-0-4-U1 36.5 mHz IN7-0-4-0 567 mHz 3c:75:4a:9c:7b:92 w-online(pt) 10.109.238.61 42.2 -0.5 33.9 -14.4 34.6 4.9E-006 0.0E+000 199 4 12:20:33 AM rC2 0  

所需的輸出將是如下:

00:15:D0:E3:B0:41           10.106.156.129
2C:9E :5F DE:ED:36           10.113.52.11
E4:83:99:6D:57:AD           10.113.45.239
3C:75:4A:9C:7B:92           10.109.238.61

,我已是如下所述的代碼:

#GET INPUT FROM CLIPBOARD 
set Input [sh_set clipboard] 
#REMOVE ALL EXCESSIVE WHITESPACE 
regsub -all {\s{3,}} $Input "\n" CleanInput 
#SET THE INPUT AS LIST 
set List [split $CleanInput "\n"] 
#GET LIST ITEMS 
set Cust1 [lindex $List 1] 
set Cust2 [lindex $List 2] 
set Cust3 [lindex $List 3] 
set Cust4 [lindex $List 4] 
regexp -all {(?:[[:xdigit:]]{2}([.-:]))(?:[[:xdigit:]]{2}\1){4}[[:xdigit:]]{2}} $Cust1 C1MacAddress 
regexp -all {10\.(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){2}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)} $Cust1 C1IpAddress 
regexp -all {(?:[[:xdigit:]]{2}([.-:]))(?:[[:xdigit:]]{2}\1){4}[[:xdigit:]]{2}} $Cust2 C2MacAddress 
regexp -all {10\.(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){2}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)} $Cust2 C2IpAddress 
regexp -all {(?:[[:xdigit:]]{2}([.-:]))(?:[[:xdigit:]]{2}\1){4}[[:xdigit:]]{2}} $Cust3 C3MacAddress 
regexp -all {10\.(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){2}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)} $Cust3 C3IpAddress 
regexp -all {(?:[[:xdigit:]]{2}([.-:]))(?:[[:xdigit:]]{2}\1){4}[[:xdigit:]]{2}} $Cust4 C4MacAddress 
regexp -all {10\.(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){2}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)} $Cust4 C4IpAddress 
return "$C1MacAddress\t$C1IpAddress\n$C2MacAddress\t$C2IpAddress\n$C3MacAddress\t$C3IpAddress\n$C4MacAddress\t$C4IpAddress" 
+0

有什麼問題awk將在這裏幫助,TCL似乎是一個矯枉過正 – Drakosha

+0

真的只是爲了變得更好,我知道有一個'foreach'可以做得比我少得多,我通常可以計算出如何做一些工作......我現在正在研究簡化我的代碼,使其高效工作 – CK1

+0

** TCL完成這個任務的原因是我使用了一個運行它的程序,我使用PcShorthand 10來自動執行很多重複的工作,該程序對於那些輸入很多。** – CK1

回答

0

好吧,假設我們要從一個txt文件加載它,那會是怎樣我會做到這一點:

set input [open "file.txt" r] 
set output [open "output.txt" w] 
set count 1 

while {[gets $input line] != -1} { 
    if {$line == ""} {continue} #Skip empty lines 
    regexp -all {(\w{2}:\w{2}:\w{2}:\w{2}:\w{2}:\w{2})} $line - MacAddress #trap the mac address and store into $MacAddress 
    regexp -all {(\d+\.\d+\.\d+\.\d+)} $line - IpAddress #trap the IP address and store into $IpAddress 
    puts $output "Customer $count: $MacAddress $IpAddress" 
    incr count 
} 

close $input 
close $output 

我只是在想這可能是幻想,如果你能說哪些客戶是^^。如果您不需要額外的功能,您可以刪除「Customer $ count」部分以及任何涉及「$ count」的行。

或者,如果輸入的數據以表格形式(這意味着你需要的信息是在同一列中,我會去:

set input [open "file.txt" r] 
set output [open "output.txt" w] 
set count 1 

while {[gets $input line] != -1} { 
    if {$line == ""} {continue} #Skip empty lines 
    regsub -all { +} $line " " newline #trims excess spaces 
    set MacAddress [lindex [split $line " "] 6] 
    set MIpAddress [lindex [split $line " "] 8] 
    puts $output "Customer $count: $MacAddress $IpAddress" 
    incr count 
} 

close $input 
close $output 
+0

謝謝你回覆的一切。正如我所說的,我正在學習TCL,並瞭解如何改進我的工作。 – CK1

2

這裏是我的解決方案:

# read entire file 
set fid [open file.txt r] 
set txt [read $fid] 
close $fid 

# split into lines 
set lines0 [split $txt \n] 

# take only non-empty lines 
set lines {} 
foreach line $lines0 { 
    if {[string trim $line] ne ""} { 
     lappend lines $line 
    } 
} 

# extract the required data from each line 
foreach line $lines { 
    set data [regexp -inline {(\w{2}:\w{2}:\w{2}:\w{2}:\w{2}:\w{2})\s+\S+\s+ (\d+.\d+.\d+.\d+)} $line] 
    foreach {dummy x y} $data { 
     puts "$x\t$y" 
    } 
} 

我使用的搜索爲6 2-字符字由冒號分隔的圖案的正則表達式,然後是字的空間,隨後通過一個屬ace(\ s + \ S + \ s +)則表示ip地址的模式。

正則表達式返回三重奏列表(這是平坦的,不是列表的列表),其中每個三重奏由整個匹配組成,然後是第一個parnthesis匹配,然後是第二個匹配。因此,虛擬變種。

或者,您可以使用正則表達式,因爲每行的單詞數量相同。由於TCL,你可以把一個字符串作爲ALIST,其項目由空間被分拆結構,可以通過更簡單地提取您的數據:

foreach line $lines { 
    set x [lindex $line 6] 
    set y [lindex $line 8] 
    puts "$x\t$y" 
}