JSON i typy generyczne w Javie - ostrzeżenie dotyczące bezpieczeństwa typu

Translate

Mam dane zapisane w elementach Java i muszę je zwrócić w podanym formacie - JSONObject. Chociaż moja implementacja działa poprawnie, nadal otrzymuję ostrzeżenie od eclipse (wersja: Juno Service Release 2):

"Bezpieczeństwo typów: metoda put (Object, Object) należy do surowego typu HashMap. Odwołania do typu ogólnego HashMap powinny być sparametryzowane"

To jest mój kod:

public interface Element {...}

public abstract class AbstractElement implements Element {...}

public final class Way extends AbstractElement {...}

import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.json.simple.JSONArray;
import org.json.simple.JSONObject;

public class WayToJsonConverter{
    ...
    public JSONObject wayToJson(){
        JSONObject obj = new JSONObject();
        obj.put("id",way.getId());
        ...
        return obj;
    }
    ...
}

Problematyczna linia to:obj.put("id",way.getId());

Czy istnieje sposób rozwiązania tego problemu inny niż dodanie@SuppressWarnings("unchecked")?

This question and all comments follow the "Attribution Required."

Wszystkie odpowiedzi

Translate

Jaki jest Twój obiekt JSONObject, czy dziedziczy on po HashMap? Jeśli tak, ostrzeżenie prawdopodobnie oznacza, że powinieneś zadeklarować instancję JSONObject w następujący sposób:

JSONObject<String,Object> obj=new JSONObject<String,Object>();

Zaktualizowano: Spójrz na definicję JSONObject:

public class JSONObject extends HashMap

rozszerza HashMap, ale nie obsługuje typu parametru, jeśli jego definicja to

public class JSONObject<K,V> extends HashMap<K,V>

wtedy moglibyśmy pisać

JSONObject<String,Object> obj=new JSONObject<String,Object>();

a metoda put nie będzie już generować ostrzeżenia

Źródło
Translate

Jeśli nie możesz przełączyć się do innej biblioteki lub zmodyfikować kodu tej biblioteki, aby była ogólna, jedyną inną opcją byłoby napisanie opakowania wokół tej biblioteki, która jej używa i poprawnie obsługuje typy generyczne.

Więc miałbyś swój własnyJSONObjectklasa, która zawierałabyorg.json.simple.JSONObject, rozszerzy sięHashMap<String, Object>i wdrożyćMap<String, Object>, i zawierałoby metody przekazywania dla wszystkich metodorg.json.simple.JSONObject.

Nadal musiałbyś położyć@SuppressWarnings("unchecked")w tej klasie, ale byłby ograniczony do tej klasy, a cała reszta twojego kodu może być wolna od ogólnych ostrzeżeń lub ich pomijania.

Źródło
Translate

public class JSONObject rozszerza HashMap implementuje Map, JSONAware, JSONStreamAware

Ale nie ma parametru typu w definicji klasy, jedyną dostępną opcją jest dodanie @SuppressWarnings („niezaznaczone”)

Źródło
Translate

Możesz utworzyć obiekt mapy, a następnie wykonać jawne rzutowanie na JSONObject

Map<String, String> obj =  new HashMap<String, String>();
obj.put("id",way.getId());
JSONObject jsonObj =  (JSONObject) obj;

Pamiętaj jednak, że ograniczy to umieszczanie w JSON tylko „ciągów znaków”. i zobaczysz błędy kompilacji, jeśli umieścisz inną strukturę danych. Powiedz tablicę.

Źródło
Translate

FYIorg.codehaus.jettison.json.JSONObjectnie spowoduje tego ostrzeżenia. Korzystając z JSONObject firmy codehaus, masz również możliwość przechwytywania błędów analizy za pomocąorg.codehaus.jettison.json.JSONException. Widziećhttps://github.com/codehaus/jettisondla szczegółów.

Źródło
Translate

Inną opcją jest zainicjowanieJSONObjectz (sparametryzowany)Map<String, Object>. W ten sposób wartość może być dowolnego prawidłowego typu JSON i unikniesz rozszerzeniauncheckedostrzeżenie. Na przykład:

public class WayToJsonConverter{
    ...
    public JSONObject wayToJson(){
        Map<String, Object> forJsonObj = new HashMap<>();
        forJsonObj.put("id",way.getId());  // No warning, hurray!
        forJsonObj.put("integer", 14);
        forJsonObj.put("floating", 1.4);
        JSONObject obj = new JSONObject(forJsonObj);
        ...
        return obj;
    }
    ...
}
Źródło
Leave a Reply
You must be logged in to post a answer.
O autorze