聊聊实际开发中经常遇到的DOM中Property和Attribute问题

来源:互联网 发布:知乎 英文新闻网站 编辑:程序博客网 时间:2024/05/16 14:49

在JavaScript中,每个DOM节点都是一个Object对象,都有自己的property和method,原则上property应该仅供js操作,不会出现在html中(非自定义的默认属性除外)。同时,attribute也出现在DOM中,在DOM API中提供了getAttribute/setAttribute方法来获取和改变它的值,最后作用于html中。此两者的取值经常相同,但是在实际项目开发中也经常会踩坑。笔者曾经在项目中也陷过此坑,同时又恰逢即将到来的面试,故做了一些简单测试,总结于此。

本文从两个大方面,六个小角度,N多个小点分别进行测试。

一、针对<input type="text" />中value类的非布尔值属性进行测试

1.默认属性未显式定义

  1. 通过两种方法读取初始值
    这里写图片描述
  2. 通过attribute来设置value的值,通过property来读取value的值
    这里写图片描述
  3. 通过property来设置value的值,通过attribute来读取value的值
    这里写图片描述

通过上边三个图可以发现,当默认属性未显式定义的时候,用两种方法读取初始值得到的是不同的结果。在进行赋值操作上,使用attribute方法赋值在更新HTML的同时也会同步更新property的值,但是反过来则不然。

在测试的过程中,笔者还发现,在3.的基础上再次进行2.来测试,然后发现当通过property设置过一次之后,此后即使再通过attribute来设置都改变不了property的读取值了,为了方便称呼,这里把它称为“X问题”,至于为什么会是这样的情况,还没有搞清楚。
这里写图片描述

2.默认属性显式定义

  1. 通过两种方法读取初始值
    这里写图片描述
  2. 通过attribute来设置value的值,通过property来读取value的值
    这里写图片描述
  3. 通过property来设置value的值,通过attribute来读取value的值
    这里写图片描述

通过上边三个图可以发现,当默认属性显式定义的时候,用两种方法读取初始值得到的是相同的结果。在进行赋值操作上,使用attribute方法赋值在更新HTML的同时也会同步更新property的值,但是反过来则不然。

“X问题”存在。
这里写图片描述

3.自定义属性未显示定义

  1. 通过两种方法读取初始值
    这里写图片描述
  2. 通过attribute来设置value的值,通过property来读取value的值
    这里写图片描述
  3. 通过property来设置value的值,通过attribute来读取value的值
    这里写图片描述

从上边三个图片可以看出,对于自定义属性当未显式定义的时候,用两种方法读出来的值为undefinednull,在进行赋值操作的时候,attribute方法更新了HTML但是没有同步更新property的值,同样,property方法也还是不能更新attribute的值。

由于本身对于自定义属性未显式定义情况下两种方法都不能同步更新对方,所以“X问题”在此也就没有意义了。
这里写图片描述

4.自定义属性显式定义

  1. 通过两种方法读取初始值
    这里写图片描述
  2. 通过attribute来设置value的值,通过property来读取value的值
    这里写图片描述
  3. 通过property来设置value的值,通过attribute来读取value的值
    这里写图片描述

在自定义属性显式定义情况下,attribute方法可以读取初始值但是property方法是不可以的。对于赋值操作和“X问题”,与自定义属性未显式定义情况下是相同的。
这里写图片描述

二、针对<input type="checkbox" />中checked类的布尔值属性进行测试

1.初始状态未选中情况

这里写图片描述

  1. 通过attribute来设置选中状态并再次取消
    这里写图片描述
    但是当需要取消选中状态的时候,attribute方法就做不到了,无论是将checked属性设置为true还是'',由于checked属性接收的是字符串,所以true会被转化为'true'进而实效,而''传入后变为单属性模式,也是选中状态,如图所示。
    这里写图片描述
  2. 通过property来设置选中状态并再次取消
    这里写图片描述
    再次取消的时候为
    这里写图片描述
    这时候就解释了为何在很多实际项目中,checkbox等布尔类型控件在选择时候只有第一次生效,之后就再也取消不掉。

2.初始状态选中的情况

这里写图片描述
- 通过property来设置取消选中状态
当处于选中状态时候,想要取消如上测试只能使用property方法来实现。
这里写图片描述

作为一篇完整的文章,结论应该是必须有的。综上所述,笔者也就自以为是的在这里简单总结几句:

  • 针对于自定义的属性,attributeproperty方法都只是自己玩闹,不涉及同步问题;
  • 针对于非自定义属性,当属性类型为value类等非布尔型的属性时,使用attribute方法会同步更新property的值,反之则不然,所以在此情况下attributeproperty方法都可以使用,但是由于attribute方法会同步在HTML上,便于调试;
  • 针对于非自定义属性,当属性类型为checked类等布尔型的属性时,由于attribute方法只接受字符串的局限性导致可以选中一次而无法取消,但是property方法不存在这个问题,既可以选中又可以取消。
  • 最后想到JQuery中的attr()方法和prop()方法,用法也是一样的,因为其源代码中attr()方法使用setAttribute/getAttribute实现,而prop()方法采用elem[key] = value / return elem[key]实现。

原创申明:由于笔者水平有限,难免会出现错误,为了便于及时更正错误,如需转载,烦请注明出处。


更多咨询欢迎微信扫描二维码,一起学习前端开发,遨游互联网。
这里写图片描述

0 0
原创粉丝点击