当对象中使用的nodeType()在jQuery版本“1.11.2”和“3.1.1”中表现不同时

时间:2017-05-23 11:51:01

标签: javascript jquery

我很想知道为什么jQuery版本'1.11.2'和'3.1.1'在jQuery对象中使用nodeType()函数时以两种不同的方式运行。

为了说明这一点,我为这两个版本提供了两个小提琴链接。

的jquery-1.11.2
 https://jsfiddle.net/38z9m9j9/9/

的jquery-3.1.1
 https://jsfiddle.net/38z9m9j9/8/

在这方面,我的条件是,

this.options.data == data.colors[0];

对于对象'this.options.data.colors [0]'使用' nodeType()'函数,仅在版本'1.11.2'中相同,其中不在'3.1中工作2.1' 。那么,'nodeType()'在'1.11.2'中是如何工作的?

提前致谢。

2 个答案:

答案 0 :(得分:4)

这两个版本的jQuery中函数isPlainObject的实现差异导致问题的原因。

  

当前isPlainObject在1.4测试.nodeType中因为IE使dom节点看起来像对象。这有$ .isPlainObject({nodeType:...})的副作用;当它应该返回true时将返回false。 (来自jQuery Forum

使用jQuery 1.11.2

var data = {
  colors: {
    id: 1,
    color: "red",
    nodeType: function () {},
  }
};

function logPlain (value, log) {
	value && value.color == "red" && $('#plain').text(log);
}

//from release of jQuery UI-1.12.1
$.widget.extend = function( target ) {
	var widgetSlice = Array.prototype.slice;
  var input = widgetSlice.call( arguments, 1 );
	var inputIndex = 0;
	var inputLength = input.length;
	var key;
	var value;

	for ( ; inputIndex < inputLength; inputIndex++ ) {
		for ( key in input[ inputIndex ] ) {
			value = input[ inputIndex ][ key ];
			if ( input[ inputIndex ].hasOwnProperty( key ) && value !== undefined ) {

				// Clone objects
				if ( $.isPlainObject( value ) ) {
          logPlain(value, 'true');
					target[ key ] = $.isPlainObject( target[ key ] ) ?
						$.widget.extend( {}, target[ key ], value ) :

						// Don't extend strings, arrays, etc. with objects
						$.widget.extend( {}, value );

				// Copy everything else by reference
				} else {
          logPlain(value, 'false');
					target[ key ] = value;
				}
			}
		}
	}
	return target;
};

$(function() {
  $.widget("custom.widget2", {
    options: {
      data: null
    },
    _create: function() {
      var isDataEqual = this.options.data == data.colors;
      $('#equal').text(isDataEqual ? "true" : "false");
    },
  });

  $("#my-widget1").widget2({
    data: data.colors
  });

});
#equal, #plain {
  background-color: rgba(0, 128, 0, 0.31);
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.2/jquery.min.js"></script>
<script src="https://code.jquery.com/ui/1.12.1/jquery-ui.min.js"></script>
<div>
  <div id="my-widget1">Testing 'nodeType' in jQuery version-1.11.2</div>
  <div>isPlainObject: <span id="plain"></div>
  <div>isDataEqual: <span id="equal"></span></div>
</div>

使用jQuery 3.1.1:

var data = {
  colors: {
    id: 1,
    color: "red",
    nodeType: function () {},
  }
};

function logPlain (value, log) {
	value && value.color == "red" && $('#plain').text(log);
}

//from release of jQuery UI-1.12.1
$.widget.extend = function( target ) {
	var widgetSlice = Array.prototype.slice;
  var input = widgetSlice.call( arguments, 1 );
	var inputIndex = 0;
	var inputLength = input.length;
	var key;
	var value;

	for ( ; inputIndex < inputLength; inputIndex++ ) {
		for ( key in input[ inputIndex ] ) {
			value = input[ inputIndex ][ key ];
			if ( input[ inputIndex ].hasOwnProperty( key ) && value !== undefined ) {

				// Clone objects
				if ( $.isPlainObject( value ) ) {
          logPlain(value, 'true');
					target[ key ] = $.isPlainObject( target[ key ] ) ?
						$.widget.extend( {}, target[ key ], value ) :

						// Don't extend strings, arrays, etc. with objects
						$.widget.extend( {}, value );

				// Copy everything else by reference
				} else {
          logPlain(value, 'false');
					target[ key ] = value;
				}
			}
		}
	}
	return target;
};

$(function() {
  $.widget("custom.widget2", {
    options: {
      data: null
    },
    _create: function() {
      var isDataEqual = this.options.data == data.colors;
      $('#equal').text(isDataEqual ? "true" : "false");
    },
  });

  $("#my-widget1").widget2({
    data: data.colors
  });

});
#equal, #plain {
  background-color: rgba(0, 128, 0, 0.31);
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
<script src="https://code.jquery.com/ui/1.12.1/jquery-ui.min.js"></script>
<div>
  <div id="my-widget1">Testing 'nodeType' in jQuery version-3.1.1</div>
  <div>isPlainObject: <span id="plain"></div>
  <div>isDataEqual: <span id="equal"></span></div>
</div>

在创建新的jQuery UI小部件时调用堆栈:

  • _createWidget(选项)
  • $ .tidget.extend({},options)
  • $。isPlainObject(options.colors)

如果$.isPlainObject(options.colors) == true则将options.colors克隆到新对象options(jQuery 3.1.1)中。 isDataEqual将是假的。

否则options.colors通过引用复制到新对象options(jQuery 1.11.0)。 isDataEqual将是真的。

为什么呢?在方法$.isPlainObject中的jQuery 1.11.2中,有以下检查:

if ( !obj || jQuery.type(obj) !== "object" || obj.nodeType || jQuery.isWindow( obj ) ) {
    return false;
}

因此,如果对象中存在属性nodeType,方法$.isPlainObject将返回false

答案 1 :(得分:0)

当我比较两个版本的jquery时,我发现jquery的isPlainObject方法有所区别,这是你的比较。如果从1.x isPlainObject方法替换3.x isPlainObject方法,则会得到与1.x相同的结果

请找截图进行比较。

enter image description here