You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Dart中正确映射泛型基础模型BaseResponse的Result属性

解决Dart泛型BaseResponse的JSON映射问题

当前自定义的BaseResponse<T>泛型模型无法将JSON中的result字段正确映射为复杂模型(如嵌套AddressModel的SampleModel)或简单类型(如String),核心问题在于Dart泛型的类型擦除机制,导致fromJson无法自动推断并解析泛型类型。


1. 修改BaseResponse的fromJson方法,添加类型解析回调

Dart运行时会擦除泛型类型信息,因此需要在fromJson中传入自定义解析函数,用来将json['result']转换为目标类型T。

修改后的BaseResponse代码:

class BaseResponse<T> {
  final bool error;
  final String? message;
  final T? result;

  const BaseResponse({required this.error, this.message, this.result});

  // 添加解析T的回调函数参数
  factory BaseResponse.fromJson(
    Map<String, dynamic> json,
    T Function(dynamic) fromJsonT,
  ) {
    final bool error = json['error'] as bool;
    final String? message = json['message'] as String?;
    // 使用传入的解析函数处理result
    final T? result = json['result'] != null ? fromJsonT(json['result']) : null;

    return BaseResponse(error: error, message: message, result: result);
  }
}

2. 为复杂模型添加fromJson方法

对于SampleModel和AddressModel这类嵌套模型,需要各自实现fromJson工厂方法来完成嵌套解析:

class AddressModel {
  final String street;
  final String city;

  AddressModel({required this.street, required this.city});

  factory AddressModel.fromJson(Map<String, dynamic> json) {
    return AddressModel(
      street: json['street'] as String,
      city: json['city'] as String,
    );
  }
}

class SampleModel {
  final String firstName;
  final String lastName;
  final AddressModel address;

  SampleModel({required this.firstName, required this.lastName, required this.address});

  factory SampleModel.fromJson(Map<String, dynamic> json) {
    return SampleModel(
      firstName: json['firstName'] as String,
      lastName: json['lastName'] as String,
      // 解析嵌套的AddressModel
      address: AddressModel.fromJson(json['address'] as Map<String, dynamic>),
    );
  }
}

3. 调用示例(复杂类型+简单类型)

在HTTP请求回调中,根据result的目标类型传入对应的解析函数:

解析复杂类型(SampleModel)

import 'dart:convert';
import 'package:http/http.dart' as http;

void main() {
  Future<void> getResponse() async {
    final response = await http.get(Uri.parse('https://getsomething.com'));

    // 检查响应状态等逻辑
    if (response.statusCode == 200) {
      final jsonData = jsonDecode(response.body) as Map<String, dynamic>;
      // 传入SampleModel.fromJson作为解析函数
      final baseResponse = BaseResponse<SampleModel>.fromJson(
        jsonData,
        (data) => SampleModel.fromJson(data as Map<String, dynamic>),
      );
      
      // 使用baseResponse.result(类型为SampleModel?)
      print(baseResponse.result?.firstName);
    }
  }

  getResponse();
}

解析简单类型(如String)

如果result是简单类型,直接传入类型转换逻辑即可:

final baseResponse = BaseResponse<String>.fromJson(
  jsonData,
  (data) => data as String,
);

内容的提问来源于stack exchange,提问作者Jeremy Trpka

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.30 01:43:26