プロパティの値を取得し、特定の文字を置き換えて別のプロパティにコピーする簡単な方法はありますか?
言ってくださいpropA=This is a value
。私は、その結果、アンダースコアにその中のすべてのスペースを置き換えたいですpropB=This_is_a_value
。
回答:
Ant Contribのpropertyregexタスクを使用します。
私はあなたが望むと思います:
<propertyregex property="propB"
input="${propA}"
regexp=" "
replace="_"
global="true" />
残念ながら、与えられた例はひどく明確ではありませんが、それを試す価値はあります。また、アンダースコアがない場合はどうなるかを確認する必要がありdefaultValue
ます。オプションを使用する必要がある場合もあります。
スクリプトなしのソリューションであり、ant-conribのような外部jarはありません。
コツは、ANTのリソースを使用することです。
<loadresource property="propB">
<propertyresource name="propA"/>
<filterchain>
<tokenfilter>
<filetokenizer/>
<replacestring from=" " to="_"/>
</tokenfilter>
</filterchain>
</loadresource>
これは、propAのすべての ""を "_"に置き換え、結果をpropBに配置します。「filetokenizer」は、入力ストリーム全体(プロパティ)を1つのトークンとして扱い、それに文字列置換を適用します。
他のtokenfiltersを使用して他の空想的な変換を行うことができます:http ://ant.apache.org/manual/Types/filterchain.html
<filetokenizer/>
少し落とすことさえできることがわかりました。コードはそれなしでも問題なく機能します(少なくともAnt v1.8.3では)。
ant
で機能し、追加のライブラリを必要としないテクニックに賛成票を投じてください。
ant-contribを使用できない場合は、Java 1.6以降用のポータブルソリューションを以下に示します。
<property name="before" value="This is a value"/>
<script language="javascript">
var before = project.getProperty("before");
project.setProperty("after", before.replaceAll(" ", "_"));
</script>
<echo>after=${after}</echo>
replaceAll
文字列用の関数がありません。before.replace( /\s/g, "_" )
代わりに使用してください。
project.getProperty()
はを返すjava.lang.String
のでreplaceAll()
、この場合は適切です。あなたが使用したい場合replace()
、あなたはネイティブJavaScriptの文字列にして「前に」変換することができます:before = new String(before);
project.setNewProperty
setProperty
古いプロパティ値を上書きできるため、移植性が向上します。before
プロパティに書き込むこともできます。
Antビルトインのみを使用するソリューションが必要な場合は、次のことを考慮してください。
<target name="replace-spaces">
<property name="propA" value="This is a value" />
<echo message="${propA}" file="some.tmp.file" />
<loadfile property="propB" srcFile="some.tmp.file">
<filterchain>
<tokenfilter>
<replaceregex pattern=" " replace="_" flags="g"/>
</tokenfilter>
</filterchain>
</loadfile>
<echo message="$${propB} = "${propB}"" />
</target>
出力は ${propB} = "This_is_a_value"
2つの可能性:
スクリプトタスクと組み込みのJavaScriptエンジンを介して(jdk> = 1.6を使用している場合)
<project>
<property name="propA" value="This is a value"/>
<script language="javascript">
project.setProperty('propB', project.getProperty('propA').
replace(" ", "_"));
</script>
<echo>$${propB} => ${propB}</echo>
</project>
またはAntアドオンFlakaを使用する
<project xmlns:fl="antlib:it.haefelinger.flaka">
<property name="propA" value="This is a value"/>
<fl:let> propB := replace('${propA}', '_', ' ')</fl:let>
<echo>$${propB} => ${propB}</echo>
</project>
既存のプロパティpropAを上書きするには、propBをpropAに置き換えるだけです
これは、Uwe Schindlerの回答のより一般化されたバージョンです。
を使用しmacrodef
てカスタムタスクを作成できます。
<macrodef name="replaceproperty" taskname="@{taskname}">
<attribute name="src" />
<attribute name="dest" default="" />
<attribute name="replace" default="" />
<attribute name="with" default="" />
<sequential>
<loadresource property="@{dest}">
<propertyresource name="@{src}" />
<filterchain>
<tokenfilter>
<filetokenizer/>
<replacestring from="@{replace}" to="@{with}"/>
</tokenfilter>
</filterchain>
</loadresource>
</sequential>
</macrodef>
これは次のように使用できます。
<replaceproperty src="property1" dest="property2" replace=" " with="_"/>
これを複数回実行している場合、これは非常に便利です。
Antプロパティの文字を置き換えるための参考情報-Maven実行内でこれを使用しようとしている場合、Maven変数を直接参照することはできません。次のようなものが必要になります。
...
<target>
<property name="propATemp" value="${propA}"/>
<loadresource property="propB">
<propertyresource name="propATemp" />
...
" "
に関連するパーツは何"_"
ですか?
propATemp
置き換えることで<propertyresource name="propATemp"/>
で<string value="${propA}"/>
プロパティは変更できませんが、antContrib変数(http://ant-contrib.sourceforge.net/tasks/tasks/variable_task.html)は変更できます。
varで検索/置換を行うマクロは次のとおりです。
<macrodef name="replaceVarText">
<attribute name="varName" />
<attribute name="from" />
<attribute name="to" />
<sequential>
<local name="replacedText"/>
<local name="textToReplace"/>
<local name="fromProp"/>
<local name="toProp"/>
<property name="textToReplace" value = "${@{varName}}"/>
<property name="fromProp" value = "@{from}"/>
<property name="toProp" value = "@{to}"/>
<script language="javascript">
project.setProperty("replacedText",project.getProperty("textToReplace").split(project.getProperty("fromProp")).join(project.getProperty("toProp")));
</script>
<ac:var name="@{varName}" value = "${replacedText}"/>
</sequential>
</macrodef>
次に、次のようにマクロを呼び出します。
<ac:var name="updatedText" value="${oldText}"/>
<current:replaceVarText varName="updatedText" from="." to="_" />
<echo message="Updated Text will be ${updatedText}"/>
上記のコードでは、正規表現よりも高速なjavascript split then joinを使用しています。「ローカル」プロパティはJavaScriptに渡されるため、プロパティリークはありません。
または... 自分のタスクを試すこともできます
Javaコード:
class CustomString extends Task{
private String type, string, before, after, returnValue;
public void execute() {
if (getType().equals("replace")) {
replace(getString(), getBefore(), getAfter());
}
}
private void replace(String str, String a, String b){
String results = str.replace(a, b);
Project project = getProject();
project.setProperty(getReturnValue(), results);
}
..all getter and setter..
ANT SCRIPT
...
<project name="ant-test" default="build">
<target name="build" depends="compile, run"/>
<target name="clean">
<delete dir="build" />
</target>
<target name="compile" depends="clean">
<mkdir dir="build/classes"/>
<javac srcdir="src" destdir="build/classes" includeantruntime="true"/>
</target>
<target name="declare" depends="compile">
<taskdef name="string" classname="CustomString" classpath="build/classes" />
</target>
<!-- Replacing characters in Ant property -->
<target name="run" depends="declare">
<property name="propA" value="This is a value"/>
<echo message="propA=${propA}" />
<string type="replace" string="${propA}" before=" " after="_" returnvalue="propB"/>
<echo message="propB=${propB}" />
</target>
コンソール:
run:
[echo] propA=This is a value
[echo] propB=This_is_a_value
defaultValue="${propA}"
は、一般的な検索/置換のワンライナーとして完璧です。それ以外の場合、一致がない場合、propBには何も入力されません。ありがとう!