Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why is json behaving in this weird manner?

Tags:

java

json

Is there any reserve words for JSON as a KEY?

my Json structure is

dimObject{String:String}
finalObject(String:dimObject}

Line1# JSONObject dimObject=new JSONObject()
Line2# dimObject.put("class",["A","B","c"]);
Line3# dimObject.put("name",["sam"]);
Line4# System.out.print("dimObject#"+dimObject.toString());
Line5# JSONObject finalObject=new new JSONObect();
Line6# finalObject("supplier",dimObject);
Line7# System.out.print("finalObject#"+finalObject.toString());

OUTPUT:

dimObject#{"class":["A","B","c"],"name":["sam"]}
finalObject#{"supplier":{"name":["sam"]}}

So the problem is why my json is behaving in a weird manner.
I have not defined "class" as variable name, it's just a Key.

Problem is ,if an argument is given like,"class" is a key or reserve word then how i successfully inserted in Line#2,and if its insert able in dimObject then why its not insert able in finalObject.

Please help me solving this mystery

EXACT CODE::

public JSONObject getRequiredAttributesWithValues() {
        List<UserConstraint> constraintList = new ArrayList<UserConstraint>();
        Map<String, FactTableOptimizingInfo> factTableMap = MappingInfo.INSTANCE.
                getFactTableUserNameToFactTableOptimizingInfoMap();
        Map<String, DimensionTableInfo> dimTableMap = MappingInfo.INSTANCE.getDimTableRealNameToObjectMap();
        JSONObject requiredAttributes = getRequiredAttributes();
        JSONObject finalObject = new JSONObject();
        for (Object dimName : requiredAttributes.keySet()) {
            JSONObject dimObject = new JSONObject();
            JSONArray colNames = requiredAttributes.getJSONArray((String) dimName);
            for (Object colName : colNames) {
                List<String> columnList = new ArrayList<String>();
                String dimensionName = (String) dimName;
                String columnName = (String) colName;
                constraintList = new ArrayList<UserConstraint>();
                for (FilterDataStructure filter : this.info.getGlobalFilterList()) {
                    if (filter.getDimName().equals(dimensionName)) {
                        if (filter.getColumnName().equals(columnName)) {
                            AtomicConstraint.ConstraintType type;
                            try {
                                Integer.parseInt(filter.getValue());
                                type = AtomicConstraint.ConstraintType.INTEGER_TYPE;
                            } catch (NumberFormatException e) {
                                type = AtomicConstraint.ConstraintType.STRING_TYPE;
                            }
                            UserConstraint constraint = new UserAtomicConstraint(dimensionName, columnName, 
                                                        AtomicConstraint.getStringToOperator(filter.getOperator()),
                                                        filter.getValue(), type, factTableMap, dimTableMap);
                            constraintList.add(constraint);
                        }
                    }
                }

                columnList.add(columnName);
                List<UserDimensionInfoToBuildQuery> dimList = new ArrayList<UserDimensionInfoToBuildQuery>();
                UserTableAndColInfo groupByInfo = new UserTableAndColInfo(dimensionName, columnName);
                ArrayList<UserTableAndColInfo> groupByInfoList = new ArrayList<UserTableAndColInfo>();
                groupByInfoList.add(groupByInfo);

                UserDimensionInfoToBuildQuery dim = new UserDimensionInfoToBuildQuery(dimensionName, columnList);
                dimList.add(dim);
                UserInfoToBuildQuery.Builder queryBuilder = new UserInfoToBuildQuery.Builder(dimList).
                        groupBy(groupByInfoList);
                if (constraintList != null && !(constraintList.isEmpty())) {
                    if (constraintList.size() > 1) {
                        queryBuilder = queryBuilder.constraints(new UserComplexConstraint(constraintList,
                                ComplexConstraint.Joiner.AND));
                    } else {
                        queryBuilder = queryBuilder.constraints(constraintList.get(0));
                    }
                }
                List<Object> result = (List<Object>) DataAccessor.getData(queryBuilder.build());
                if (result == null) {
                    continue;
                }
                JSONArray valueArray = new JSONArray();

                for (Object row : result) {
                    List<Object> splitRow = (List<Object>) row;
                    valueArray.add(splitRow.get(0).toString());
                }
                dimObject.put(colName, valueArray);
            }
            finalObject.put(dimName, dimObject);
        }
        return finalObject;
    }
}
like image 703
Ashish Agarwal Avatar asked Jan 21 '10 18:01

Ashish Agarwal


People also ask

Why does my JSON string have backslash?

Those backslashes are escape characters. They are escaping the special characters inside of the string associated with JSON response. You have to use JSON. parse to parse that JSON string into a JSON object.

Why is JSON unordered?

The JSON Data Interchange Standard definition at json.org specifies that “An object is an unordered [emphasis mine] set of name/value pairs”, whereas an array is an “ordered collection of values”. In other words, by definition the order of the key/value pairs within JSON objects simply does not, and should not, matter.

Does order matter in JSON?

The JSON RFC (RFC 4627) says that order of object members does not matter.

Is JSON unordered?

Yes, the order of elements in JSON arrays is preserved. From RFC 7159 -The JavaScript Object Notation (JSON) Data Interchange Format (emphasis mine): An object is an unordered collection of zero or more name/value pairs, where a name is a string and a value is a string, number, boolean, null, object, or array.


3 Answers

As to follow up with your observation, JSON follows JavaScript (or ECMAScript, as it should be called) reserved words and class is one of them.

EDIT:

While dabbling with javascript, it seems you can use reserve words within quotation marks, I have tested it as follows:

myObj = {"class" : "Analysis of Algorithms"}; // <--works
myObj = { class  : "Analysis of Algorithms"}; //  <--works
myObj = { class  : "class"}; // <--works
myObj = {"class" :  class }; // <--does not work.

As well it is interesting, I am still puzzled by the problem. With JSON I am using all my techniques with javascript, so I cannot produce the same results as you can.

I found the source file for JSONObject.java at this website

like image 117
Anthony Forloney Avatar answered Oct 07 '22 14:10

Anthony Forloney


Edit: In your example, you're writing code in Java. I don't know what Java implementation of JSON you're using, but it's probably not strict. It's not meant to be a JavaScript interpreter or engine, so it's not preventing you from doing something you shouldn't do. That's why you can add the "class" key like you did -- the Java side is going to let you do that even though it's wrong. It's not checking to make sure you're not using keywords as identifiers. When that JSON gets interpreted by a web browser after it's left the Java world, you will have problems, because now that "class" word has a special meaning.

class is a reserved word. You should avoid using it as a variable name. See here for a list of reserved words.

Chrome's JavaScript console let me use it as an identifier. IE8 behaves differently. I can't use it in dot notation but I can use it with bracket notation. See a.class and a['class'] in the following.

>>var class = "1"
  "Expected identifier"
>>var a = "1"
undefined
>>a
"1"
>>class
  "Syntax error"
>>var a = {}
undefined
>>a["foo"] = "1"
"1"
>>a["class"] = "2"
"2"
>>a.class
  "Expected identifier"
>>a.foo
"1"
>>a['foo']
"1"
>>a['class']
"2"

The point is, don't use reserved words as identifiers. You probably won't get the results you expect.

like image 32
Jonathon Faust Avatar answered Oct 07 '22 14:10

Jonathon Faust


the reason JSON uses { "double quotes":"around key/vals" } is for this exact reason - to escape reserved words.

that said, if you are getting valid JSON, there should be no problems, as any reserved words will be escaped by the "double quotes"...

I noticed you have a missing quote in this line:

finalObject#{"supplier:{"name":["sam"]}}

should be "supplier". is there anyway you could change that? or is it being auto generated?

like image 22
Dan Beam Avatar answered Oct 07 '22 12:10

Dan Beam