13 JavaScript关于prototype(超重点)

prototype是js里面给类增加功能扩展的一种模式.

写个面向对象来看看.

function People(name, age){
this.name = name;
this.age = age;
this.run = function(){
console.log(this.name+"在跑")
}
} p1 = new People("张三", 18);
p2 = new People("李四", 19); p1.run();
p2.run();

我现在代码写完了. 突然之间, 我感觉好像少了个功能. 人不应该就一个功能. 光会跑是不够的. 还得能够ooxx. 怎么办? 直接改代码? 可以. 但不够好. 如果这个类不是我写的呢? 随便改别人代码是很不礼貌的. 也很容易出错. 怎么办? 我们可以在我们自己代码中对某个类型动态增加功能. 此时就用到了prototype.

function People(name, age){
this.name = name;
this.age = age;
this.run = function(){
console.log(this.name+"在跑")
}
} // 通过prototype可以给People增加功能
People.prototype.xxoo = function(){
console.log(this.name+"还可以xxoo");
} p1 = new People("张三", 18);
p2 = new People("李四", 19); p1.run();
p2.run(); p1.xxoo();
p2.xxoo();

能看到一些效果了是吧. 也就是说. 可以通过prototype给我们的对象增加一些功能.

接下来. 聊几个重要的概念.

  1. 构造器

    构造一个对象的函数. 叫构造器.
function People(){  //这个东西就是构造器 constractor

}

var p = new People(); // 调用构造器
p.constractor == People; // true
  1. 原型对象

    每一个js对象中. 都有一个隐藏属性__proto__指向该对象的原型对象. 在执行该对象的方法或者查找属性时. 首先, 对象自己是否存在该属性或者方法. 如果存在, 就执行自己的. 如果自己不存在. 就去找原型对象.
function Friend(){
this.chi = function(){
console.log("我的朋友在吃");
}
}
Friend.prototype.chi = function(){
console.log("我的原型在吃")
} f = new Friend();
f.chi(); // 此时. 该对象中. 有chi这个方法. 同时, 它的原型对象上, 也有chi这个方法.
// 运行结果:
// 我的朋友在吃
  1. prototype__proto__有什么关系?

    在js中. 构造器的prototype属性和对象的__proto__是一个东西. 都是指向这个原型对象.
f.__proto__ === Friend.prototype   // true
  1. 原型链

    这个比较绕了. 我们从前面的学习中, 了解到. 每个对象身体里. 都隐藏着__proto__也就是它的原型对象. 那么我们看哈, 原型对象也是对象啊, 那么也就是说. 原型对象也有__proto__属性.

类似于.....这样:

f.__proto__.__proto__

打印出来的效果是这样的:



此时. 又出现一堆看不懂的玩意. 这些玩意是什么? 这些其实是Object的原型.

f.__proto__.__proto__ === Object.prototype

所以, 我们在执行f.toString()的时候不会报错. 反而可以正常运行. 原因就在这里.

执行过程: 先找f对象中是否有toString. 没有, 找它的原型对象.原型对象中没有, 继续找原型对象的原型对象. 直至你找到Object的原型为止. 如果还是没有. 就报错了.

f.hahahahahahah()  // 报错.

综上, 原型链是js 方法查找的路径指示标.

5. 我们用原型链能做什么?(每日一恶心)

我们来看一段神奇的代码.

(function(){debugger})();

这样一段代码可以看到. 浏览器进入了debugger断点.

那么这段代码的背后是什么呢? 注意. 在js代码执行时. 每一个function的对象都是通过Function()来创建的. 也就是说. 函数是Function()的对象.

function fn(){}

console.log(fn.proto.constructor); // ƒ Function() { [native code] }

这样一段代码可以看到. 浏览器进入了debugger断点.

那么这段代码的背后是什么呢? 注意. 在js代码执行时. 每一个function的对象都是通过Function()来创建的. 也就是说. 函数是Function()的对象.

function fn(){}
console.log(fn.__proto__.constructor); // ƒ Function() { [native code] }

函数就是Function的对象. 那么. 我们可以通过Function来构建一个函数.

new Function('debugger')();

OK. 这东西对我们来说有什么用. 上代码

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<script src="haha.js"></script>
<script>
txsdefwsw();
</script>
</head>
<body>
有内鬼. 终止交易
</body>
</html>

haha.js 中的内容如下:

function txsdefwsw() {
var r = "V", n = "5", e = "8"; function o(r) {
if (!r) return "";
for (var t = "", n = 44106, e = 0; e < r.length; e++) {
var o = r.charCodeAt(e) ^ n;
n = n * e % 256 + 2333, t += String.fromCharCode(o)
}
return t
} try {
var a = ["r", o("갯"), "g", o("갭"), function (t) {
if (!t) return "";
for (var o = "", a = r + n + e + "7", c = 45860, f = 0; f < t.length; f++) {
var i = t.charCodeAt(f);
c = (c + 1) % a.length, i ^= a.charCodeAt(c), o += String.fromCharCode(i)
}
return o
}("@"), "b", "e", "d"].reverse().join("");
!function c(r) {
(1 !== ("" + r / r).length || 0 === r) && function () {
}.constructor(a)(), c(++r)
}(0)
} catch (a) {
setTimeout(txsdefwsw, 100);
}
}

页面跑起来没什么问题. 但是会无限debugger;

解决方案:

  1. 找到断点出. 右键-> never pause here;
  2. 写js hook代码;
var x = Function; // 保留原来的Function
Function = function(arg){
arg = arg.replace("debugger", "");
return new x(arg);
} var qiaofu_function_constructor = (function(){}).__proto__.constructor;
(function(){}).__proto__.constructor = function(arg){
console.log("我爱你大大");
if(arg ==='debugger'){
return function(){}
} else {
return new qiaofu_function_constructor(arg);
}
}

[[prototype]]
__proto__
构造器.prototype
function jiami(){ }
jiami.prototype.md5 = function(){}
jiami.prototype.aes = function(){}
jiami.prototype.encrypt = function(){}
var s = new jiami();
s.md5();

13 JavaScript关于prototype(超重点)的更多相关文章

  1. JavaScript学习13 JavaScript中的继承

    JavaScript学习13 JavaScript中的继承 继承第一种方式:对象冒充 <script type="text/javascript"> //继承第一种方式 ...

  2. Javascript Array.prototype.some()

    当我们使用数组时,查找数组中包含某个特殊的项是非常常见的动作.下面例子是一个简单的实现: 01 planets = [ 02     "mercury", 03     " ...

  3. Javascript中prototype属性详解 (存)

    Javascript中prototype属性详解   在典型的面向对象的语言中,如java,都存在类(class)的概念,类就是对象的模板,对象就是类的实例.但是在Javascript语言体系中,是不 ...

  4. javascript 之 prototype 浅析

    prototype 原型 javascript 是一种 prototype based programming 的语言, 而与我们通常的 class based programming 有很大 的区别 ...

  5. Javascript: 从prototype漫谈到继承(2)

    本文同时也发表在我另一篇独立博客 <Javascript: 从prototype漫谈到继承(2)>(管理员请注意!这两个都是我自己的原创博客!不要踢出首页!不是转载!已经误会三次了!) 上 ...

  6. JavaScript 笔记 ( Prototype )

    这阵子实在好忙 ( 这样说好像也不是一两个月了... ),然后因为工作伙伴都是 JavaScript 神之等级的工程师,从中也学到不少知识,毕竟就是要和强者工作才会成长呀!为了想好好瞭解他们写的程式码 ...

  7. JavaScript和prototype

    Protoype这个词在javascript中可以有两种理解: 第一种是作为javascript中的一个属性,其一般出现的形式为:类名.prototype. prototype 属性让你有能力向对象添 ...

  8. 在 JavaScript 中 prototype 和 __proto__ 有什么区别

    本文主要讲三个 问题 prototype 和 proto function 和 object new 到底发生了什么 prototype 和 proto 首先我们说下在 JS 中,常常让我们感到困惑的 ...

  9. javascript继承—prototype最优两种继承(空函数和循环拷贝)

    一.利用空函数实现继承 参考了文章javascript继承-prototype属性介绍(2) 中叶小钗的评论,对这篇文章中的方案二利用一个空函数进行修改,可以解决创建子类对象时,父类实例化的过程中特权 ...

  10. 13.JavaScript 类

    JavaScript 类 JavaScript 是面向对象的语言,但 JavaScript 不使用类. 在 JavaScript 中,不会创建类,也不会通过类来创建对象(就像在其他面向对象的语言中那样 ...

随机推荐

  1. 硬件开发笔记(三):硬件开发基本流程,制作一个USB转RS232的模块(二):设计原理图库

    前言   上一篇了解了基本的过程,选型了相关的芯片,本篇描述原理图的设计过程,在原理图设计之前或者过程中需要不断新增原理图元器件.   Allegro.OrCad   Cadence公司针对PCB方面 ...

  2. 数据结构(三):舞伴配对问题(C++,队列)

    好家伙, 题目如下: 1.舞伴配对问题:假设在周末舞会上,男士们和女士们进入舞厅时,各自排成一队.跳舞开始时,依次从男队和女队的队头上各出一人配成舞伴. 2.若两队初始人数不相同,则较长的那一队中未配 ...

  3. webpack图片压缩

    减少代码体积 | 尚硅谷 Web 前端之 Webpack5 教程 (yk2012.github.io) npm install image-mininizer webpack plugin image ...

  4. 【Azure 应用服务】使用Docker Compose创建App Service遇见"Linux Version is too long. It cannot be more than 4000 characters"错误

    问题描述 使用Docker Compose方式合并多个镜像(Images)文件,然后部署到App Service中,结果失败.报错 Linux Version 太长,不能超过4000个字符. 错误消息 ...

  5. 【Azure 环境】中国区Azure B2C 是否支持手机验证码登录呢?

    问题描述 中国区Azure B2C 是否支持手机验证码登录呢? 问题回答 在没有原生 Phone sign-up and sign-in for user flows (中国区不支持,Global A ...

  6. 浅入Kubernetes(4):使用Minikube体验

    Minikube 打开 https://github.com/kubernetes/minikube/releases/tag/v1.19.0 下载最新版本的二进制软件包(deb.rpm包),再使用 ...

  7. 智联招聘基于 Nebula Graph 的推荐实践分享

    本文首发于 Nebula Graph Community 公众号 本文整理自智联招聘资深工程师李世明在「智联招聘推荐场景应用」的实践分享 搜索推荐架构 在讲具体的应用场景之前,我们先看下智联招聘搜索和 ...

  8. C# 课堂管理系统(火影忍者界面!!!)

    1 using System; 2 using System.Collections.Generic; 3 using System.Linq; 4 using System.Text; 5 usin ...

  9. Python项目维护不了?可能是测试没到位。Django的单元测试和集成测试初探

    前言 好久没搞 Django 了,最近维护一个我之前用 Django 开发的项目竟然有亲切的感觉 测试,在以前确实是经常被忽略的话题,特别是对于 Python Web 这种快速开发框架,怎么敏捷怎么来 ...

  10. putty配置kali linux 远程连接

    首先配置sshd_config文件 VI 编辑或者使用 gedit 文本编辑, 修改的内容包括下面几个 红色标出(为了以复原建议大家 拷贝一份或者修改的地方进行标注) 之后重启服务,但是有的还是存在报 ...