Smart HO
Smart HO

Reputation: 169

Flutter: Join specific field of JSON file together to become a list itself

I have a json file with a list of different types of data.

I wanted to join the "name" field of all attractions of each city together as a list. The expected result after joining, for example for Longo city will be like this:

Attraction1

Attraction2

The data in JSON file is structured like this:

  {
    "city": "London",
    "attractions": [
      {
        "name": "Attraction1",
        "localrank": 10,
        "intrank": 4
      },
      {
        "name": "Attraction2",
        "localrank": 4,
        "intrank": 5
      }
    ]
  },
  {
    "city": "Hong Kong",
    "attractions": [
      {
        "name": "Attraction3",
        "localrank": 10,
        "intrank": 4
      },
      {
        "name": "Attraction4",
        "localrank": 4,
        "intrank": 5
      }
    ]
  },
  {
    "city": "Cario",
    "attractions": [
      {
        "name": "Attraction5",
        "localrank": 10,
        "intrank": 4
      },
      {
        "name": "Attraction6",
        "localrank": 4,
        "intrank": 5
      }
    ]
  }
] 

I used the following code, but I get an error :

cities.attractions.name.join("\n")

Json model class is this:

List<Cities> citiesFromJson(String str) =>
    List<Cities>.from(json.decode(str).map((x) => Cities.fromJson(x)));
String citiesToJson(List<Cities> data) =>
    json.encode(List<dynamic>.from(data.map((x) => x.toJson())));

class Cities {
  Cities({
    this.city,
    this.attractions,
  });

  String city;
  List<Attraction> attractions;

  factory Cities.fromRawJson(String str) => Cities.fromJson(json.decode(str));

  String toRawJson() => json.encode(toJson());

  factory Cities.fromJson(Map<String, dynamic> json) => Cities(
        city: json["city"],
        attractions: List<Attraction>.from(
            json["attractions"].map((x) => Attraction.fromJson(x))),
      );

  Map<String, dynamic> toJson() => {
        "city": city,
        "attractions": List<dynamic>.from(attractions.map((x) => x.toJson())),
      };
}

class Attraction {
  Attraction({
    this.name,
    this.localrank,
    this.intrank,
  });

  String name;
  int localrank;
  int intrank;

  factory Attraction.fromRawJson(String str) =>
      Attraction.fromJson(json.decode(str));

  String toRawJson() => json.encode(toJson());

  factory Attraction.fromJson(Map<String, dynamic> json) => Attraction(
        name: json["name"],
        localrank: json["localrank"],
        intrank: json["intrank"],
      );

  Map<String, dynamic> toJson() => {
        "name": name,
        "localrank": localrank,
        "intrank": intrank,
      };
}

And this also calling json file:

  Future<String> fetchData() async {
    String data =
        await DefaultAssetBundle.of(context).loadString("assets/data.json");
    final jsonResult = json.decode(data);
    print('$jsonResult oop');
    this.setState(() {
      jsonResult.forEach(
          (element) => Globals.citylist.add(new Cities.fromJson(element)));
    });
    return "Success!";
  }

Upvotes: 1

Views: 889

Answers (1)

ChessMax
ChessMax

Reputation: 2265

Something like that should work:

import 'dart:convert';

var data = """  [{
    "city": "London",
    "attractions": [
      {
        "name": "Attraction1",
        "localrank": 10,
        "intrank": 4
      },
      {
        "name": "Attraction2",
        "localrank": 4,
        "intrank": 5
      }
    ]
  },
  {
    "city": "Hong Kong",
    "attractions": [
      {
        "name": "Attraction3",
        "localrank": 10,
        "intrank": 4
      },
      {
        "name": "Attraction4",
        "localrank": 4,
        "intrank": 5
      }
    ]
  },
  {
    "city": "Cario",
    "attractions": [
      {
        "name": "Attraction5",
        "localrank": 10,
        "intrank": 4
      },
      {
        "name": "Attraction6",
        "localrank": 4,
        "intrank": 5
      }
    ]
  }
] """;

List<Cities> citiesFromJson(String str) =>
    List<Cities>.from(json.decode(str).map((x) => Cities.fromJson(x)));
String citiesToJson(List<Cities> data) =>
    json.encode(List<dynamic>.from(data.map((x) => x.toJson())));

class Cities {
  Cities({
    this.city,
    this.attractions,
  });

  String city;
  List<Attraction> attractions;

  factory Cities.fromRawJson(String str) => Cities.fromJson(json.decode(str));

  String toRawJson() => json.encode(toJson());

  factory Cities.fromJson(Map<String, dynamic> json) => Cities(
    city: json["city"],
    attractions: List<Attraction>.from(
        json["attractions"].map((x) => Attraction.fromJson(x))),
  );

  Map<String, dynamic> toJson() => {
    "city": city,
    "attractions": List<dynamic>.from(attractions.map((x) => x.toJson())),
  };
}

class Attraction {
  Attraction({
    this.name,
    this.localrank,
    this.intrank,
  });

  String name;
  int localrank;
  int intrank;

  factory Attraction.fromRawJson(String str) =>
      Attraction.fromJson(json.decode(str));

  String toRawJson() => json.encode(toJson());

  factory Attraction.fromJson(Map<String, dynamic> json) => Attraction(
    name: json["name"],
    localrank: json["localrank"],
    intrank: json["intrank"],
  );

  Map<String, dynamic> toJson() => {
    "name": name,
    "localrank": localrank,
    "intrank": intrank,
  };
}

class Globals {
  static List<Cities> citylist = [];
}

Future<String> fetchData() async {
  // String data =
  // await DefaultAssetBundle.of(context).loadString("assets/data.json");
  final jsonResult = json.decode(data);
  print('$jsonResult oop');
  // this.setState(() {
    jsonResult.forEach(
            (element) => Globals.citylist.add(new Cities.fromJson(element)));
  // });

  var result = getAttractionsByCity('London');

  print(result.join('\n'));

  return "Success!";
}

List<String> getAttractionsByCity(String value) {
  var result = <String>[];

  for (final city in Globals.citylist) {
    if (city.city == value) {
      final attractions = city.attractions;

      for (final attraction in attractions) {
        result.add(attraction.name);
      }
    }
  }

  return result;
}

void main() async {
  await fetchData();
}

It's a working example. You can copy and paste this code to HTTP://dartpad.dev and run it to see the result.

Upvotes: 1

Related Questions