web-dev-qa-db-ja.com

ハッシュマップキーを反復処理するFreemarker

Freemarkerには、リストとハッシュマップという2つのコレクションデータ型がありますリストと同じようにハッシュマップキーを反復処理する方法はありますか?

したがって、データを持つ変数がある場合、次のように言うことができます:

user : {
  name : "user"
  email : "[email protected]"
  homepage : "http://nosuchpage.org"
}

すべてのユーザーのプロパティとその値を印刷したいと思います。これは無効ですが、目標は明確です。

<#list user.props() as prop>
  ${prop} = ${user.get(prop)}
</#list>
81
tzador

Edit:このソリューションをFreeMarker 2.3.25以降、特に.get(prop)では使用しないでください。他の回答をご覧ください。

組み込みの keys 関数を使用します。これは動作するはずです:

<#list user?keys as prop>
    ${prop} = ${user.get(prop)}
</#list>  
101
skaffman

参考までに、値を取得するための構文は次のように変更されているようです。

http://freemarker.sourceforge.net/docs/ref_builtins_hash.html

<#assign h = {"name":"mouse", "price":50}>
<#assign keys = h?keys>
<#list keys as key>${key} = ${h[key]}; </#list>
50
Nick Spacek

2.3.25以降、次のようにします。

_<#list user as propName, propValue>
  ${propName} = ${propValue}
</#list>
_

これは、文字列以外のキーでも機能することに注意してください(map?api.get(key)として記述しなければならなかった_map[key]_とは異なります)。

2.3.25より前の標準ソリューションは次のとおりでした。

_<#list user?keys as prop>
  ${prop} = ${user[prop]}
</#list>
_

ただし、一部の本当に古いFreeMarker統合では、パブリックMapメソッド(getClassなど)がキーとして表示される奇妙な構成を使用します。これは、BeansWrapperプロパティがDefaultObjectWrapperに残された(simpleMapWrapperの代わりに)純粋なfalseを使用しているために発生します。メソッドを実際のMapエントリと混合するため、このようなセットアップは避けてください。しかし、このような不幸なセットアップに遭遇した場合、状況を回避する方法は、公開されたJavaメソッド(user.entrySet()user.get(key)など)を使用することです。 。、および_?keys_や_user[key]_などのテンプレート言語構造を使用しない。

40
ddekany

Expose.SAFEまたはExpose.ALLの露出レベルで BeansWrapper を使用する場合、エントリセットを反復する標準のJavaアプローチを使用できます。

たとえば、次はFreemarkerで動作します(少なくともバージョン2.3.19以降):

<#list map.entrySet() as entry>  
  <input type="hidden" name="${entry.key}" value="${entry.value}" />
</#list>

たとえば、Struts2では、 BeanWrapperの拡張 が使用され、デフォルトの露出レベルでこの方法を使用できます。

12
rees

反復オブジェクト

マップキーが文字列ではなくオブジェクトである場合、Freemarkerを使用して反復できます。

1)コントローラーでマップをリストに変換します。

List<Map.Entry<myObjectKey, myObjectValue>> convertedMap  = new ArrayList(originalMap.entrySet());

2)Freemarkerテンプレートでマップを繰り返し、キーのオブジェクトと値のオブジェクトにアクセスします。

<#list convertedMap as item>
    <#assign myObjectKey = item.getKey()/>
    <#assign myObjectValue = item.getValue()/>
    [...]
</#list>
2
Tk421

単一引用符を使用して、Javaプログラムで設定したキーにアクセスできます。

Javaのようにマップを設定した場合

Map<String,Object> hash = new HashMap<String,Object>();
hash.put("firstname", "a");
hash.put("lastname", "b");

Map<String,Object> map = new HashMap<String,Object>();
map.put("hash", hash);

次に、このようにFreemarkerの「ハッシュ」のメンバーにアクセスできます-

${hash['firstname']}
${hash['lastname']}

出力:

a
b
1
Ashish Chhabria

完全を期すために、最近からFreemarkerで空のコレクションを適切に処理していることに言及する価値があります。

したがって、マップを反復する最も便利な方法は次のとおりです。

<#list tags>
<ul class="posts">
    <#items as tagName, tagCount>
        <li>{$tagName} (${tagCount})</li>
    </#items>
</ul>
<#else>
    <p>No tags found.</p>
</#list>

もういや <#if ...>ラッパー。

0
Ondra Žižka