找回密码
 加入
搜索
查看: 5181|回复: 14

[AU3基础] 请教一下各位关于字符串操作的问题~~(已解决)

 火.. [复制链接]
发表于 2011-3-8 22:15:52 | 显示全部楼层 |阅读模式
本帖最后由 annybaby 于 2011-3-27 21:19 编辑

有一个文本文件保存着如下内容

A1       4.5      8.9      90      ABCD
RSE2   5.62   2.77     0        CC
HS1     -1.98  -2.577  45      ABCD
C300  58.75   5.7       180   ESD

上面的规律描述起来比较麻烦:

每一行分成五个部分(由空格或TAB键分开 第一部分和第五部分是一般字符串,中间的三部分是数,
长度可能不同,有正有负(如果处理有难度,可以当全部是正的)

我需要做的:

比较第五部分,如果是一样的话(比如上面的第一行和第三行,大家都是“ABCD”,那么需要记录下来,比如赋值给某个变量,然后将内容进行一些变换,再写到一个新建的文件里面去,比如说,上面的内容,我希望转换成下面这样的

A1       +004.500      +008.900      90     1   -    ABCD
HS1     -001.980       -002.577       45     1   -    ABCD
RSE2   +005.620      +002.770      0       2   -    CC
C300   +008.750      +005.700     180    3   -    ESD

上面转换后变成了七部分,第五部分中数字按自然数增加,表示种类,如果第七部分在前面已经出现过,则第五部分的数字与其一致,比如上面的:
第二行第七部分也是“ABCD”,与第一行的第七部分一样,所以对应的第五部分也与其一致,都是“1”
而第三行的"CC",由于前面没有出现过,所以对应的第五部分就按自然数增加1,变成“2”,第三行同样道理~~

拜托各位高手啦~~
发表于 2011-3-8 23:49:56 | 显示全部楼层
基本上是纯体力活,改数字格式比较麻烦…… 另,照现在的规律
C300   +008.750      +005.700     180    3   -    ESD
应该是
C300   +058.750      +005.700     180    3   -    ESD
 楼主| 发表于 2011-3-9 00:03:03 | 显示全部楼层
回复 2# afan


    对,不好意思,是我打错啦,
 楼主| 发表于 2011-3-9 00:08:11 | 显示全部楼层
基本上是纯体力活,改数字格式比较麻烦…… 另,照现在的规律
C300   +008.750      +005.700     180     ...
afan 发表于 2011-3-8 23:49



数字格式用stringformat()应该可以吧??
我最不会的是如何准确读取到里面的各个部分,正则表达式也不会用~~
发表于 2011-3-9 00:16:21 | 显示全部楼层
本帖最后由 www378660084 于 2011-3-9 00:17 编辑

输入text.txt (tab分割)
A1        4.5        8.9        90        ABCD
RSE2        5.62        2.77        0         CC
HS1        -1.98        -2.577        45        ABCD
C300        58.75         5.7        180        ESD
输出out.txt(在这显示有点问题)
A1        +004.500        +008.900        90        1        -        ABCD
HS1        -001.980        -002.577        45        1        -        ABCD
RSE2        +005.620        +002.770        0         2        -        CC
C300        +058.750        +005.700        180        3        -        ESD
#include <Array.au3>
Global $lineNum = 0
Global $lines[10]
Global $sortIndex[10] = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
Global $lineArr[10][5]



;读取文件
Global $filein = FileOpen("text.txt", 0)
Local $str
$str = FileReadLine($filein)
While $str <> ""
        $lineNum += 1
        $lines[$lineNum] = $str
        $str = FileReadLine($filein)
WEnd
FileClose($filein)
Local $i, $j, $tmpArr[5]
For $i = 1 To $lineNum
        $tmpArr = StringSplit($lines[$i], "        ")
        ;_ArrayDisplay($tmpArr)
        For $j = 0 To 4
                If $j = 1 Or $j = 2 Then
                        $lineArr[$i][$j] = format($tmpArr[$j + 1])
                Else
                        $lineArr[$i][$j] = $tmpArr[$j + 1]
                EndIf
        Next
Next
;排列
Local $tmp
For $i = 1 To $lineNum
        For $j = $i + 1 To $lineNum
                If StringCompare($lineArr[$j][4], $lineArr[$i][4]) < 0 Then
                        $tmp = $sortIndex[$i]
                        $sortIndex[$i] = $sortIndex[$j]
                        $sortIndex[$j] = $tmp
                EndIf
        Next
Next


;写出
Global $fileout = FileOpen("out.txt", "2")
Local $num = 1
For $i = 1 To $lineNum
        $str = $lineArr[$sortIndex[$i]][0]
        If $i > 1 And $lineArr[$sortIndex[$i]][4] <> $lineArr[$sortIndex[$i - 1]][4] Then $num += 1
        For $j = 1 To 3
                $str = $str & "        " & $lineArr[$sortIndex[$i]][$j]
        Next
        $str = $str & "        " & $num & "        " & "-" & "        " & $lineArr[$sortIndex[$i]][4]
        FileWriteLine($fileout, $str)
Next

Func format($str)
        Local $ret = "", $tmp = ""
        Local $num = Number($str)
        Local $int = Int($num)
        $num = Abs($num - $int)
        $ret = StringFormat("%+04d", $int)
        $tmp = StringFormat("%.3f", $num)
        $tmp = StringReplace($tmp, "0.", ".")
        $ret = $ret & $tmp
        Return $ret
EndFunc   ;==>format
 楼主| 发表于 2011-3-13 17:27:09 | 显示全部楼层
回复 5# www378660084


    谢谢先,不过我运行了下,输出如下


A1        +000.000        +000.000                1        -        
RSE2        +000.000        +000.000                1        -        
HS1        +000.000        +000.000                1        -        
C300        +000.000        +000.000                1        -        

即:可以是这样

A1        +004.500        +008.900        90        1        -        ABCD
HS1        -001.980        -002.577        45        1        -        ABCD
RSE2        +005.620        +002.770        0         2        -        CC
C300        +058.750        +005.700        180        3        -        ESD

也可以是这样:

A1        +004.500        +008.900        90        1        -        ABCD
RSE2        +005.620        +002.770        0         2        -        CC
C300        +058.750        +005.700        180        3        -        ESD
HS1        -001.980        -002.577        45        1        -        ABCD

另外,你程序里面的排列我看不懂

我有这样的想法,但是不会用循环实现

按您前面的方法,将内容保存到一个二维数组里面,比如$array[1][4]存放着第一行[ABCD],然后用数组的一个位置存放一个标志,比如$array[][5]初始化为0,从第二行开始,与之比较,相同的话,就用一个标志记录,比如输入中第三行也是"ABCD",就可以将$array[3][5]改成1,依此类推,一直到尾,然后第二次从第二行开始,先判断是否与前一轮比较有相同的(看$array[2][5]是否为1),如果是表明和第一行的是一样的,直接执行下一次循环,如果不同,表明是一个新元素,直接加1,即
$array[2][5]=2,然后后面又逐行比较~~


我用for 循环搞了一下下午都没有成功~~
发表于 2011-3-13 19:30:56 | 显示全部楼层
#include <Array.au3>

Local $avArray[4][5] = [['A1', '4.5', '8.9', '90', 'ABCD'], ['RSE2', '5.62', '2.77', '0', 'CC'], ['HS1', '-1.98', '-2.577', '45', 'ABCD'], ['C300', '58.75', '5.7', '180', 'ESD']]
_ArrayDisplay($avArray, "默认排序方式" )
_ArraySort($avArray, 0, 0, 0, 0)
_ArrayDisplay($avArray, "副索引0升序排列方式" )
_ArraySort($avArray, 0, 0, 0, 1)
_ArrayDisplay($avArray, "副索引1升序排列方式" )
_ArraySort($avArray, 0, 0, 0, 2)
_ArrayDisplay($avArray, "副索引2升序排列方式" )
.....
发表于 2011-3-13 20:23:35 | 显示全部楼层
#include <array.au3>
#include <file.au3>
local $array
_FileReadToArray("bb.txt",$array)
local $out_array[UBound($array)][7],$k=1,$str
for $i=1 to $array[0]
        $temp=StringSplit(StringStripWS($array[$i],4),chr(32),2)
        $temp[1]=_format($temp[1])
        $temp[2]=_format($temp[2])
        for $n=0 to 3
                $out_array[$i][$n]=$temp[$n]
        Next
        $out_array[$i][5]='-'
        $out_array[$i][6]=$temp[4]
        if not IsDeclared($temp[4]) then 
                Assign($temp[4],$k)
                $k+=1
        EndIf
Next

;_ArraySort($out_array,0,0,0,6);如果需要排序

for $i=1 to $array[0]
        if IsDeclared($out_array[$i][6]) then $out_array[$i][4]=Eval($out_array[$i][6])
Next

_ArrayDisplay($out_array)
for $i=1 to UBound($out_array)-1
        for $n=0 to UBound($out_array,2)-1
                $str&=$out_array[$i][$n]&@TAB
        Next
        $str&=@CRLF
Next
msgbox(0,0,$str)

func _format($num)
        return StringFormat('%+04d',$num)&StringTrimLeft(StringFormat('%.3f',StringRegExpReplace($num,'(.+)(?=\.)','')),1)
EndFunc
发表于 2011-3-13 20:49:38 | 显示全部楼层
本帖最后由 kevinch 于 2011-3-13 20:52 编辑

这种用excel处理好点吧,可以直接将格式修改成想要的这样。
直接用excel打开那个文本文件,将B,C列设置自定义数字格式
+000.000;-000.000;0;@
最后一列添加内容后排序,添加序号,然后保存即可
发表于 2011-3-13 22:09:32 | 显示全部楼层
做个例子,最近也一直在研究AU3与office软件间的调用方法,附件供测试。

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?加入

×
 楼主| 发表于 2011-3-13 22:50:24 | 显示全部楼层
本帖最后由 annybaby 于 2011-3-14 19:58 编辑

谢谢各位的回帖,慢慢研究几位的代码,特别感谢楼上用excel处理的那个test ,我再慢慢尝试学习~~
 楼主| 发表于 2011-3-14 20:42:08 | 显示全部楼层
回复 10# kevinch

谢谢你的回帖,你的结果是我最想要的,(当然,其它回复的坛友也让我学了不少东西,)但是我想去掉中间的那个"-"可以吗?
我想应该是去掉其中的几行代码,但是我不知道去掉哪几行,我试了下去掉"-"那一行,发现输出也只是少了"-",第四部分与第五部分的距离变成了两个"TAB"键的宽度...
发表于 2011-3-14 20:59:09 | 显示全部楼层
回复  kevinch

谢谢你的回帖,你的结果是我最想要的,(当然,其它回复的坛友也让我学了不少 ...
annybaby 发表于 2011-3-14 20:42


如果求代码但不学会思考的话,代码求来又有何用??
8楼代码只需要在29行,30行之间增加一句:if $n=5 then ContinueLoop即可解决你的又一个问题.
发表于 2011-3-14 21:18:29 | 显示全部楼层
发表于 2011-3-15 13:58:07 | 显示全部楼层
回复  kevinch

谢谢你的回帖,你的结果是我最想要的,(当然,其它回复的坛友也让我学了不少 ...
annybaby 发表于 2011-3-14 20:42
$excel=objcreate("excel.application")
;$excel.visible=true

$wb=$excel.workbooks.open(@scriptdir&"\test.txt")
$ws=$wb.worksheets(1)
for $row=1 to $ws.cells($ws.rows.count,1).end(3).row
        $arr=stringsplit($excel.worksheetfunction.trim($ws.cells($row,1).value)," ")
        for $column=1 to ubound($arr)-1
                $ws.cells($row,$column)=$arr[$column]
        next
next
with $ws
        .columns("B:C").numberformatlocal="+000.000;-000.000;0;@"
        .cells(1,1).currentregion.sort(.cells(1,5))
        .columns("E").insert
        $n=1
        .cells(1,5)=1
        for $row=2 to .cells(.rows.count,1).end(3).row
                if .cells($row,7).value<>.cells($row-1,7).value then $n=$n+1
                .cells($row,5)=$n
        next
endwith
$excel.application.displayalerts=False
$wb.close(true)
$excel.quit
这个试一下
您需要登录后才可以回帖 登录 | 加入

本版积分规则

QQ|手机版|小黑屋|AUTOIT CN ( 鲁ICP备19019924号-1 )谷歌 百度

GMT+8, 2024-10-2 12:22 , Processed in 0.119696 second(s), 24 queries .

Powered by Discuz! X3.5 Licensed

© 2001-2024 Discuz! Team.

快速回复 返回顶部 返回列表