0

NSISで文字列の長さを調べる方法はありますか?

ファイルが空(内容がない)かどうかをテストしようとしています。1つの方法は、ファイルを読み取り、コンテンツを文字列(contentStrと呼ばれる)に格納してから、そのcontentStr文字列の長さを確認することです。> 0の場合、空ではありません。

もう1つの方法は、contentStr == ""かどうかを確認することですが、以下に示すように、機能しません。空のファイルは、次の場合に1を返すことはありません。

!macro IsFileEmpty fName res

    !insertmacro ReadFile "${fName}" ${res}

    StrCmp ${res} "" +1 +2
    IntOp ${res} 1 + 0
    IntOp ${res} 0 + 0

!macroend
4

4 に答える 4

5

文字列の長さを取得するには、StrLenを使用します。

StrLen $0 "123456" # ==> $0 = 6

読み込もうとする前にファイルサイズを取得したい場合は、別の回答でフランシスコが指摘した手法を参照してください。

于 2012-12-19T11:36:19.620 に答える
2

ファイルサイズが本当に0バイトであることを確認しましたか?ファイルにスペースや改行文字が含まれている可能性があります...そのような場合は、文字列をStrRepまたはTrimする必要があります。

ファイルサイズを知りたいだけの場合は、次のマクロと関数を使用できます。

!macro FileSize VAR FILE
    Push "${FILE}"
    Call FileSizeNew
    Pop ${VAR}
!macroend
Function FileSizeNew 
  Exch $0
  Push $1
  FileOpen $1 $0 "r"
  FileSeek $1 0 END $0
  FileClose $1
  Pop $1
  Exch $0
FunctionEnd

詳細はこちら:

http://nsis.sourceforge.net/Getting_File_Size

于 2012-12-19T10:21:16.210 に答える
1

このようにするのは少し奇妙で、部分的にしか機能しません。

...
StrCmp ${res} "" 0 +2 ; +1 and 0 is the same, jumps to next instruction
StrCpy ${res} 1 ; No need to do math here
IntOp ${res} ${res} + 0 ; NaN + 0 = 0 but what if you read a number from the file?

ファイルが番号で始まる可能性がある場合は、zbynourが提案したようにジャンプする必要があります。

...
StrCmp ${res} "" 0 +3 
StrCpy ${res} 1
Goto +2
StrCpy ${res} 0

テストを反転すると、同じ数の命令で必要なものを取得できます。

!macro IsFileNOTEmpty fName res

  !insertmacro ReadFile "${fName}" ${res}

  StrCmp ${res} "" +2 0
  StrCpy ${res} 1 ; Or IntOp ${res} ${res} | 1 if you really wanted to do extra math ;)
  IntOp ${res} ${res} + 0

!macroend

またはさらに良い:

!macro IsFileEmpty fName res

  !insertmacro ReadFile "${fName}" ${res}

  StrLen ${res} ${res} ; If this is enough depends on how you want to deal with newlines at the start of the file (\r or \n)

!macroend

...このコードはすべて、ファイルがテキストで始まるかどうかをテストすることを前提としています。ファイルが0バイトで始まる場合は、常にファイルが空であると表示されます。したがって、ファイルにバイナリコンテンツが含まれている場合は、実際のサイズをバイト単位でテストするFranciscoRのコードを使用する必要があります。

于 2012-12-20T03:38:35.790 に答える
0

これは、最後の行が常に実行されるためです(${res}空の場合、オフセットは実行されます+1が、次の命令はスキップされません)。

次のコードは、期待どおりに機能するはずです。

!macro IsFileEmpty fName res

    !insertmacro ReadFile "${fName}" ${res}

    StrCmp ${res} "" +1 +3
    IntOp ${res} 1 + 0
    goto end
    IntOp ${res} 0 + 0
    end:

!macroend
于 2012-12-19T10:23:54.147 に答える