Как проверить, является ли объект JavaScript JSON
У меня есть вложенный объект JSON, который мне нужно пропустить, и значение каждого ключа может быть массивом String, JSON или другим объектом JSON. В зависимости от типа объекта мне нужно выполнять разные операции. Есть ли способ проверить тип объекта, чтобы увидеть, является ли он объектом String, JSON или массивом JSON?
Я попытался использовать typeof
и instanceof
, но оба они не работали, поскольку typeof
возвращает объект как для объекта JSON, так и для массива, а instanceof
дает ошибку, когда я делаю obj instanceof JSON
.
Чтобы быть более конкретным, после разбора JSON в JS-объект, есть ли способ проверить, является ли он нормальной строкой или объектом с ключами и значениями (из объекта JSON) или массивом (из массив JSON)?
Например:
JSON
var data = "{'hi':
{'hello':
['hi1','hi2']
},
'hey':'words'
}";
Пример JavaScript
var jsonObj = JSON.parse(data);
var path = ["hi","hello"];
function check(jsonObj, path) {
var parent = jsonObj;
for (var i = 0; i < path.length-1; i++) {
var key = path[i];
if (parent != undefined) {
parent = parent[key];
}
}
if (parent != undefined) {
var endLength = path.length - 1;
var child = parent[path[endLength]];
//if child is a string, add some text
//if child is an object, edit the key/value
//if child is an array, add a new element
//if child does not exist, add a new key/value
}
}
Как выполнить проверку объекта, как показано выше?
Ответы
Ответ 1
Я бы проверил атрибут конструктора.
например,
var stringConstructor = "test".constructor;
var arrayConstructor = [].constructor;
var objectConstructor = ({}).constructor;
function whatIsIt(object) {
if (object === null) {
return "null";
}
if (object === undefined) {
return "undefined";
}
if (object.constructor === stringConstructor) {
return "String";
}
if (object.constructor === arrayConstructor) {
return "Array";
}
if (object.constructor === objectConstructor) {
return "Object";
}
{
return "don't know";
}
}
var testSubjects = ["string", [1,2,3], {foo: "bar"}, 4];
for (var i=0, len = testSubjects.length; i < len; i++) {
alert(whatIsIt(testSubjects[i]));
}
Изменение: добавлена нулевая проверка и неопределенная проверка.
Ответ 2
Вы можете использовать Array.isArray для проверки массивов. Затем typeof obj == 'string' и typeof obj == 'object'.
var s = 'a string', a = [], o = {}, i = 5;
function getType(p) {
if (Array.isArray(p)) return 'array';
else if (typeof p == 'string') return 'string';
else if (p != null && typeof p == 'object') return 'object';
else return 'other';
}
console.log("'s' is " + getType(s));
console.log("'a' is " + getType(a));
console.log("'o' is " + getType(o));
console.log("'i' is " + getType(i));
's' является строкой
'a' является массивом
'o' является объектом
'i' является другим
Ответ 3
Объектом JSON является объект. Для проверки погоды любой тип является типом объекта, оцените свойство конструктора.
function isObject(obj)
{
return obj !== undefined && obj !== null && obj.constructor == Object;
}
То же самое относится ко всем другим типам:
function isArray(obj)
{
return obj !== undefined && obj !== null && obj.constructor == Array;
}
function isBoolean(obj)
{
return obj !== undefined && obj !== null && obj.constructor == Boolean;
}
function isFunction(obj)
{
return obj !== undefined && obj !== null && obj.constructor == Function;
}
function isNumber(obj)
{
return obj !== undefined && obj !== null && obj.constructor == Number;
}
function isString(obj)
{
return obj !== undefined && obj !== null && obj.constructor == String;
}
function isInstanced(obj)
{
if(obj === undefined || obj === null) { return false; }
if(isArray(obj)) { return false; }
if(isBoolean(obj)) { return false; }
if(isFunction(obj)) { return false; }
if(isNumber(obj)) { return false; }
if(isObject(obj)) { return false; }
if(isString(obj)) { return false; }
return true;
}
Ответ 4
Если вы пытаетесь проверить тип object
после синтаксического анализа строки JSON
, я предлагаю проверить атрибут конструктора:
obj.constructor == Array || obj.constructor == String || obj.constructor == Object
Это будет намного быстрее, чем typeof или instanceof.
Если библиотека JSON не возвращает объекты, построенные с этими функциями, я бы очень сомневался в ней.
Ответ 5
Вы можете создать свой собственный конструктор для разбора JSON:
var JSONObj = function(obj) { $.extend(this, JSON.parse(obj)); }
var test = new JSONObj('{"a": "apple"}');
//{a: "apple"}
Затем проверьте экземпляр instanceof, чтобы увидеть, нужно ли ему сначала выполнять синтаксический анализ
test instanceof JSONObj
Ответ 6
Ответ @PeterWilkinson не работал у меня, потому что конструктор для "типизированного" объекта настраивается под именем этого объекта. Мне пришлось работать с typeof
function isJson(obj) {
var t = typeof obj;
return ['boolean', 'number', 'string', 'symbol', 'function'].indexOf(t) == -1;
}
Ответ 7
Я написал модуль npm для решения этой проблемы. Он доступен здесь:
object-types
: модуль для поиска того, что литеральные типы недостижимы
Установка
npm install --save object-types
Использование
const objectTypes = require('object-types');
objectTypes({});
//=> 'object'
objectTypes([]);
//=> 'array'
objectTypes(new Object(true));
//=> 'boolean'
Взгляните, он должен решить вашу точную проблему. Дайте знать, если у вас появятся вопросы! https://github.com/dawsonbotsford/object-types
Ответ 8
вы также можете попытаться проанализировать данные, а затем проверить, есть ли у вас объект:
var testIfJson = JSON.parse(data);
if (typeOf testIfJson == "object")
{
//Json
}
else
{
//Not Json
}
Ответ 9
Попробуйте это
if ( typeof is_json != "function" )
function is_json( _obj )
{
var _has_keys = 0 ;
for( var _pr in _obj )
{
if ( _obj.hasOwnProperty( _pr ) && !( /^\d+$/.test( _pr ) ) )
{
_has_keys = 1 ;
break ;
}
}
return ( _has_keys && _obj.constructor == Object && _obj.constructor != Array ) ? 1 : 0 ;
}
Он работает для примера ниже
var _a = { "name" : "me",
"surname" : "I",
"nickname" : {
"first" : "wow",
"second" : "super",
"morelevel" : {
"3level1" : 1,
"3level2" : 2,
"3level3" : 3
}
}
} ;
var _b = [ "name", "surname", "nickname" ] ;
var _c = "abcdefg" ;
console.log( is_json( _a ) );
console.log( is_json( _b ) );
console.log( is_json( _c ) );
Ответ 10
Я объединяю оператор typeof с проверкой атрибута конструктора (by Peter):
var typeOf = function(object) {
var firstShot = typeof object;
if (firstShot !== 'object') {
return firstShot;
}
else if (object.constructor === [].constructor) {
return 'array';
}
else if (object.constructor === {}.constructor) {
return 'object';
}
else if (object === null) {
return 'null';
}
else {
return 'don\'t know';
}
}
// Test
var testSubjects = [true, false, 1, 2.3, 'string', [4,5,6], {foo: 'bar'}, null, undefined];
console.log(['typeOf()', 'input parameter'].join('\t'))
console.log(new Array(28).join('-'));
testSubjects.map(function(testSubject){
console.log([typeOf(testSubject), JSON.stringify(testSubject)].join('\t\t'));
});
Результат:
typeOf() input parameter
---------------------------
boolean true
boolean false
number 1
number 2.3
string "string"
array [4,5,6]
object {"foo":"bar"}
null null
undefined
Ответ 11
Питер ответит с дополнительной проверкой! Конечно, не гарантировано на 100%!
var isJson = false;
outPutValue = ""
var objectConstructor = {}.constructor;
if(jsonToCheck.constructor === objectConstructor){
outPutValue = JSON.stringify(jsonToCheck);
try{
JSON.parse(outPutValue);
isJson = true;
}catch(err){
isJson = false;
}
}
if(isJson){
alert("Is json |" + JSON.stringify(jsonToCheck) + "|");
}else{
alert("Is other!");
}
Ответ 12
Почему бы не проверить номер - немного короче и работает в IE/Chrome/FF/node.js
function whatIsIt(object) {
if (object === null) {
return "null";
}
else if (object === undefined) {
return "undefined";
}
if (object.constructor.name) {
return object.constructor.name;
}
else { // last chance 4 IE: "\nfunction Number() {\n [native code]\n}\n" / node.js: "function String() { [native code] }"
var name = object.constructor.toString().split(' ');
if (name && name.length > 1) {
name = name[1];
return name.substr(0, name.indexOf('('));
}
else { // unreachable now(?)
return "don't know";
}
}
}
var testSubjects = ["string", [1,2,3], {foo: "bar"}, 4];
// Test all options
console.log(whatIsIt(null));
console.log(whatIsIt());
for (var i=0, len = testSubjects.length; i < len; i++) {
console.log(whatIsIt(testSubjects[i]));
}
Ответ 13
попробуйте этот грязный способ
('' + obj).includes('{')