如何按前缀模式过滤POJO属性?基于Moshi转换的Item类场景
嘿,我来给你几个实用的方案,帮你轻松提取Item里所有以'a'开头的属性,根据你的场景选最适合的就行:
方案1:用反射动态提取(灵活但有性能开销)
如果你的Item类属性可能会变动,或者不想硬编码属性名,反射是个不错的选择。它能自动遍历所有字段,筛选出以'a'开头的:
import java.lang.reflect.Field; import java.util.HashMap; import java.util.Map; public class ItemUtils { public static Map<String, String> extractAStartingProperties(Item item) { Map<String, String> aProps = new HashMap<>(); Field[] fields = Item.class.getDeclaredFields(); for (Field field : fields) { field.setAccessible(true); // 允许访问私有字段 String fieldName = field.getName(); if (fieldName.startsWith("a")) { try { String value = (String) field.get(item); aProps.put(fieldName, value); } catch (IllegalAccessException e) { // 处理异常,比如打印日志 e.printStackTrace(); } } } return aProps; } }
使用的时候就遍历你的Item列表,逐个调用这个方法:
List<Item> itemList = ...; // 你的Moshi解析结果 List<Map<String, String>> allAPropsList = new ArrayList<>(); for (Item item : itemList) { allAPropsList.add(ItemUtils.extractAStartingProperties(item)); }
注意:反射会有一定的性能开销,如果你的Item列表非常大,或者需要频繁调用,建议考虑下面的方案。
方案2:在Item类里封装提取方法(高效直接)
如果Item的属性比较固定,直接在Item类里写一个方法,手动把所有'a'开头的属性整理成集合,这种方式没有反射开销,运行最快:
public class Item { private String aa; private String b; private String abc; private String ad; private String dd; private String qw; private String arew; private String tt; private String asd; private String aut; private String id; // 省略getter和setter public Map<String, String> getAStartingProperties() { Map<String, String> aProps = new HashMap<>(); aProps.put("aa", this.aa); aProps.put("abc", this.abc); aProps.put("ad", this.ad); aProps.put("arew", this.arew); aProps.put("asd", this.asd); aProps.put("aut", this.aut); // 如果后续新增了a开头的属性,记得在这里添加 return aProps; } }
使用起来也很简单:
List<Item> itemList = ...; List<Map<String, String>> allAPropsList = new ArrayList<>(); for (Item item : itemList) { allAPropsList.add(item.getAStartingProperties()); }
方案3:自定义Moshi JsonAdapter,解析时直接过滤(适合大响应场景)
如果你的服务端响应非常大,先转成完整的Item对象再提取有点浪费内存,可以自定义一个Moshi的Adapter,在解析JSON的时候就只提取'a'开头的字段,直接返回整理好的Map:
import com.squareup.moshi.FromJson; import com.squareup.moshi.JsonAdapter; import com.squareup.moshi.JsonReader; import com.squareup.moshi.Moshi; import java.io.IOException; import java.util.HashMap; import java.util.Map; public class APropsAdapter { @FromJson public Map<String, String> fromJson(JsonReader reader) throws IOException { Map<String, String> aProps = new HashMap<>(); reader.beginObject(); while (reader.hasNext()) { String name = reader.nextName(); if (name.startsWith("a")) { String value = reader.nextString(); aProps.put(name, value); } else { reader.skipValue(); // 跳过非a开头的字段,节省内存 } } reader.endObject(); return aProps; } }
然后用这个Adapter直接解析响应:
Moshi moshi = new Moshi.Builder() .add(new APropsAdapter()) .build(); JsonAdapter<List<Map<String, String>>> adapter = moshi.adapter( Types.newParameterizedType(List.class, Map.class, String.class, String.class) ); // 假设response是服务端返回的JSON字符串 List<Map<String, String>> allAPropsList = adapter.fromJson(response);
这种方式不需要创建完整的Item对象,直接过滤出需要的字段,内存占用更低,适合处理大体积的响应。
内容的提问来源于stack exchange,提问作者Igal
相关产品推荐
相关产品推荐

