GVKun编程网logo

【译】【Javascript - 真正的原型继承】(js原型继承的几种方式)

4

在本文中,我们将为您详细介绍【译】【Javascript-真正的原型继承】的相关知识,并且为您解答关于js原型继承的几种方式的疑问,此外,我们还会提供一些关于AndroidWebview和Javasc

在本文中,我们将为您详细介绍【译】【Javascript - 真正的原型继承】的相关知识,并且为您解答关于js原型继承的几种方式的疑问,此外,我们还会提供一些关于Android Webview 和 Javascript 交互,实现 Android 和 JavaScript 相互调用、href=“javascript:”vs href=“javascript:void(0)”、JavaScript - 基础入门.0002.JavaScript 快速使用、JavaScript .prototype 如何工作? - How does JavaScript .prototype work?的有用信息。

本文目录一览:

【译】【Javascript - 真正的原型继承】(js原型继承的几种方式)

【译】【Javascript - 真正的原型继承】(js原型继承的几种方式)

原文地址:Javascript – How Prototypal Inheritance really works

在网上可以看到各种关于Javascript原型继承的文章,但Javascript规范中只提供了new操作符这一种实现原型继承的方法。因此网上大多数的文章是具有迷惑性的,很混乱。这篇文章会让你清晰的认识到什么是真正的原型继承?并且怎么样使用它?

原型继承的定义:

你会经常看到如下关于原型继承的定义:

访问一个对象属性的时候,Javascript会沿着原型链向上寻找,直到找到该属性。

Javascript中大多数实现方式都是使用__proto__来指定原型链中下一个被访问的对象,接下来会揭示__proto__与prototype之间的区别。

注意:不要在你的代码中使用__proto__,文中使用它仅仅是为了更好的解释Javascript继承是如何工作的。

下面的代码展示了Javascript引擎如何检索对象的属性(伪代码,仅为了方便理解)

function getProperty(obj, prop) {
    if (obj.hasOwnProperty(prop)){
        return obj[prop];
    }else if (obj.__proto__ !== null){
        return getProperty(obj.__proto__, prop);
    }else{
        return undefined;
    }
}

举个例子:一个二维的点。拥有x坐标属性,y坐标属性和一个print方法。

用书面语言来表示该定义就是:我们定义了一个有三个属性的对象:x,y和print。为了构造一个新点,我们只需要创建一个对象并将他的__proto__属性指向Point。

var Point = {
    x: 0,
    y: 0,
    print: function () { console.log(this.x, this.y); }
};
var p = {x: 10, y: 20, __proto__: Point};
p.print(); // 10 20

奇怪的原型继承:

怪异之处在于解释原型继承的人给出的例子往往与他们的定义不相符合,他们给出的代码通常如下所示:

function Point(x, y) {
    this.x = x;
    this.y = y;
}
Point.prototype = {
    print: function () { console.log(this.x, this.y); }
};
var p = new Point(10, 20);
p.print(); // 10 20

上面所例举的代码跟原型继承完全不相关,Point是构造函数,它有一个prototype属性,使用了new操作符,但是然后呢?

new是如何工作的:

Brendan Eich 想让javascript像Java,C++这些传统的面向对象语言一样,用new操作类直接构造一个实例,所以他给Javascript也添了new操作符。

  • C++中有构造函数,用来初始化实例的属性。因此,new操作符操作的对象必须是函数。

  • 我们需要把对象的方法挂载到某个地方,由于我们使用的是原型语言,我们把他放在函数的原型属性里。

new操作符构造步骤有三步:

  1. 构造一个类的实例:这个实例是一个空对象,并且他的__proto__属性指向构造函数的原型。

  2. 初始化实例:构造函数被调用,并将this指向这个实例。

  3. 返回实例对象。

现在我们了解了new构造的过程,我们在Javascript中实现它:

function New (f) {
    var n = { ''__proto__'': f.prototype };
    return function () {
        f.apply(n, arguments);
        return n;
    };
}

举一个小例子:

function Point(x, y) {
    this.x = x;
    this.y = y;
}
Point.prototype = {
    print: function () { console.log(this.x, this.y); }
};

var p1 = new Point(10, 20);
p1.print(); // 10 20
console.log(p1 instanceof Point); // true
 
var p2 = New (Point)(10, 20);
p2.print(); // 10 20
console.log(p2 instanceof Point); // true

Javascript中真正的原型继承:

Javascript规范只定义了new操作符的工作流程,Douglas Crockford发现了一种利用new实现原型继承的新方法,他写的Object.create函数。

Object.create = function (parent) {
    function F() {}
    F.prototype = parent;
    return new F();
};

看起来很奇怪,但实际上很简洁。他只创建了一个新的对象,原型你可以随意设置。如果允许使用__proto__的话,这个例子可以这样写:

Object.create = function (parent) {
    return { ''__proto__'': parent };
};

下面这个Point例子才是真正的原型继承。

var Point = {
    x: 0,
    y: 0,
    print: function () { console.log(this.x, this.y); }
};
 
var p = Object.create(Point);
p.x = 10;
p.y = 20;
p.print(); // 10 20

结论:

我们了解了原型继承并用一种具体的方法实现了它。但这样写有一些缺点:

  • 不标准:__proto__不是标准并不赞成使用, 并且原生的 Object.create 和 Douglas Crockford的实现不等同。

  • 不优化:Object.create (原生的或自定义的)作为构造函数是及其不高效的。

Android Webview 和 Javascript 交互,实现 Android 和 JavaScript 相互调用

Android Webview 和 Javascript 交互,实现 Android 和 JavaScript 相互调用

在 Android 的开发过程中、遇到一个新需求、那就是让 Java 代码和 Javascript 代码进行交互、在 IOS 中实现起来很麻烦、而在 Android 中相对来说容易多了、Android 对这种交互进行了很好的封装、我们可以很简单的用 Java 代码调用 WebView 中的 js 函数、也可以用 WebView 中的 js 来调用 Android 应用中的 Java 代码。

案例主要包含了:

  1.  Html 中调用 Android 方法
  2. Android 调用 JS 方法无参数
  3. Android 调用 JS 方法有参数
  4. Android 调用 JS 方法有参数且有返回值处理方式 1
  5. Android 调用 JS 方法有参数且有返回值处理方式 2(Android4.4 以上)

1:创建 JS 对象

webView.addJavascriptInterface(new JsInterface(), "obj");
public class JsInterface {
	//JS中调用Android中的方法 和返回值处理的一种方法
		
	/****
          * Html中的点击事件 onclick
	  *  <input type="button" value="结算" onclick="showToast(''12'')">
	  * @param toast
	  */
	@JavascriptInterface
	public void showToast(String toast) {
	  Toast.makeText(MainActivity.this, "你的商品价格是:¥"+toast, Toast.LENGTH_SHORT).show();
	}
}
 function showToast(toast) { 
	var money=toast*3;
	javascript:obj.showToast(money);
}

2:

webView.loadUrl("javascript:funFromjs()");
function funFromjs(){
    document.getElementById("helloweb").innerHTML="div显示数据,无参数";
}

3:

webView.loadUrl("javascript:funJs(''Android端传入的信息,div标签中显示,含参数'')");
function funJs(msg){
   document.getElementById("hello2").innerHTML=msg;
}

4: 

webView.loadUrl("javascript:sum(6,6)");
/***
 * Android代码调用获取J是中的返回值
 * 
 * @param result
*/
   @JavascriptInterface
   public void onSum(int result) { 
	Toast.makeText(MainActivity.this, "Android调用JS方法且有返回值+计算结果=="+result, Toast.LENGTH_SHORT).show();
   } 
function sum(i,m){ 
    var result = i*m; 
    document.getElementById("h").innerHTML= "Android调用JS方法且有返回值--计算结果="+result; 
    javascript:obj.onSum(result) 
} 

5:

 webView.evaluateJavascript("sumn(6,11)", new ValueCallback<String>() {
         @Override
	 public void onReceiveValue(String value) {
	     Toast.makeText(MainActivity.this, "返回值"+value, Toast.LENGTH_SHORT).show();
           }
});
function sumn(i,m){ 
     var result = i*m; 
     document.getElementById("hh").innerHTML= "Android调用JS方法且有返回值--计算结果="+result; 
     return result;
} 

   注意:

1、Java 调用 js 里面的函数、效率并不是很高、估计要 200ms 左右吧、做交互性很强的事情、这种速度很难让人接受、而 js 去调 Java 的方法、速度很快、50ms 左右、所以尽量用 js 调用 Java 方法

2、Java 调用 js 的函数、没有返回值、调用了就控制不到了

3、Js 调用 Java 的方法、返回值如果是字符串、你会发现这个字符串是 native 的、转成 locale 的才能正常使用、使用 toLocaleString () 函数就可以了、不过这个函数的速度并不快、转化的字符串如果很多、将会很耗费时间

4、网页中尽量不要使用 jQuery、执行起来需要 5-6 秒、最好使用原生的 js 写业务脚本、以提升加载速度、改善用户体验。

注:使用的是本地的 Html 文件,不过在网络链接的 Html 文件也是可以实现的。   

源码点击下载

href=“javascript:”vs href=“javascript:void(0)”

href=“javascript:”vs href=“javascript:void(0)”

##href=“javascript:” vs href=“javascript:void(0)”

可参考
http://www.jb51.net/article/37904.htm
http://stackoverflow.com/questions/3666683/href-javascript-vs-href-javascriptvoid0

JavaScript - 基础入门.0002.JavaScript 快速使用

JavaScript - 基础入门.0002.JavaScript 快速使用

常用属性:

属性名称 属性说明
src 表示包含要执行代码的外部文件,常用来引用外部的 js 文件
type 表示代码使用的脚本语言的内容类型

1

2

3

4

5

6

7

8

9

10

11

12

<!DOCTYPE html>

<html>

<head>

<meta charset="UTF-8">

<title>]</title>

</head>

<body>

    <script type="text/javascript">

        alert(''Hello Word!'');

    </script>

</body>

</html>

 

注意事项:

1. 如果你想弹出一个 </script> 标签的字符串,内部 js 会误解成 Js 代码的结束,可通过 + 连接分解 </script > 将字符串分为两个部分,但是外部引用的 js 是无需加号拼接的

1

2

3

4

5

6

7

8

9

10

11

12

<!DOCTYPE html>

<html>

<head>

<meta charset="UTF-8">

<title></title>

</head>

<body>

    <script type="text/javascript">

        alert(''</scr'' ''ipt>'');

    </script>

</body>

</html>

2. Js 代码越来越庞大时,最好把它另存为一个.js 文件,通过 src 来引用,这样具有维护性高,可缓存 (加载一次,无需加载), 方便未来扩展的特点

1

2

3

4

5

6

7

8

9

10

<!DOCTYPE html>

<html>

<head>

<meta charset="UTF-8">

<title></title>

</head>

<body>

    <script type="text/javascript" src="js/main.js"></script>

</body>

</html>

3. 对于不支持 JavaScript 平稳的处理方式是通过 <noscript></noscript > 实现?

1

2

3

4

5

6

7

8

9

10

11

<!DOCTYPE html>

<html>

<head>

<meta charset="UTF-8">

<title></title>

<noscript>此网站必须启用JavaScript支持!</noscript>

</head>

<body>

    <script type="text/javascript" src="js/main.js"></script>

</body>

</html>

 

 

登录乐搏学院官网 http://www.learnbo.com/

或关注我们的官方微博微信,还有更多惊喜哦~

 

 

本文出自 “满满李 - 运维开发之路” 博客,请务必保留此出处 http://xmdevops.blog.51cto.com/11144840/1846116

JavaScript .prototype 如何工作? - How does JavaScript .prototype work?

JavaScript .prototype 如何工作? - How does JavaScript .prototype work?

问题:

I''m not that into dynamic programming languages but I''ve written my fair share of JavaScript code. 我不喜欢动态编程语言,但是我写了相当一部分 JavaScript 代码。 I never really got my head around this prototype-based programming, does any one know how this works? 我从来没有真正了解过这种基于原型的编程,有人知道它是如何工作的吗?

var obj = new Object();
obj.prototype.test = function() { alert(''Hello?''); };
var obj2 = new obj();
obj2.test();

I remember a lot discussion I had with people a while back (I''m not exactly sure what I''m doing) but as I understand it, there''s no concept of a class. 我记得很久以前与人们进行过多次讨论(我不确定自己在做什么),但是据我了解,这里没有一个课堂的概念。 It''s just an object, and instances of those objects are clones of the original, right? 这只是一个对象,这些对象的实例是原始对象的副本,对吗?

But what is the exact purpose of this ".prototype" property in JavaScript? 但是,此 “.prototype” 属性在 JavaScript 中的确切目的是什么? How does it relate to instantiating objects? 它与实例化对象有何关系?

Update: correct way 更新:正确的方法

var obj = new Object(); // not a functional object
obj.prototype.test = function() { alert(''Hello?''); }; // this is wrong!

function MyObject() {} // a first class functional object
MyObject.prototype.test = function() { alert(''OK''); } // OK

Also these slides really helped a lot. 这些幻灯片也确实起到了很大作用。


解决方案:

参考一: https://stackoom.com/question/2P2H/JavaScript-prototype 如何工作
参考二: https://oldbug.net/q/2P2H/How-does-JavaScript-prototype-work

今天的关于【译】【Javascript - 真正的原型继承】js原型继承的几种方式的分享已经结束,谢谢您的关注,如果想了解更多关于Android Webview 和 Javascript 交互,实现 Android 和 JavaScript 相互调用、href=“javascript:”vs href=“javascript:void(0)”、JavaScript - 基础入门.0002.JavaScript 快速使用、JavaScript .prototype 如何工作? - How does JavaScript .prototype work?的相关知识,请在本站进行查询。

本文标签: