十年网站开发经验 + 多家企业客户 + 靠谱的建站团队
量身定制 + 运营维护+专业推广+无忧售后,网站问题一站解决
今天遇到关于javascript原型的一道面试题,现分析下:
成都创新互联公司是一家集网站建设,二连浩特企业网站建设,二连浩特品牌网站建设,网站定制,二连浩特网站建设报价,网络营销,网络优化,二连浩特网站推广为一体的创新建站企业,帮助传统企业提升企业形象加强企业竞争力。可充分满足这一群体相比中小企业更为丰富、高端、多元的互联网需求。同时我们时刻保持专业、时尚、前沿,时刻以成就客户成长自我,坚持不断学习、思考、沉淀、净化自己,让我们为更多的企业打造出实用型网站。
原题如下:
function
A(){
}
function
B(a){
this.a
=
a;
}
function
C(a){
if(a){
this.a
=
a;
}
}
A.prototype.a
=
1;
B.prototype.a
=
1;
C.prototype.a
=
1;
console.log(new
A().a);
console.log(new
B().a);
console.log(new
C(2).a);
分析:
console.log(new
A().a);//new
A()为构造函数创建的对象,本身没有a属性,所以向它的原型去找,发现原型的a属性的属性值为1,故该输出值为1;
console.log(new
B().a);//new
B()为构造函数创建的对象,该构造函数有参数a,但该对象没有传参,故该输出值为undefined;
console.log(new
C(2).a);//new
C()为构造函数创建的对象,该构造函数有参数a,且传的实参为2,执行函数内部,发现if为真,执行this.a
=
2,故属性a的值为2;
故这三个的输出值分别为:1、undefined、2.
以上就是小编为大家带来的关于js原型的面试题讲解的全部内容了,希望对大家有所帮助,多多支持脚本之家~
求JavaScript部分 代码讲解?
if(/\((iPhone|iPad|iPod)/i.test(navigator.userAgent) == false){return;} //代表如果不是iPhone,iPad,iPod返回
document.addEventListener('mouseover', function(e){ //添加一个监听事件.当鼠标移上时执行后边的函数
var ele = e.target; //获取当前对象的打开放式
do{ //如果是A链接打开放式为在自己的窗口打开,如果是div返回,
if(ele.tagName == 'A'){
ele.target = '_self';
return;
}
if(ele.tagName == 'DIV'){return;}
ele = ele.parentNode; //然后把父节点赋值给ELE
}while(ele);
},false);
}
从0基础到勉强能用,只求入门的话2-3个月绰绰有余,但是要精通的话肯定是需要花更多时间日积月累了,选择培训的话是要参与一些项目联练习的,因为JavaScript很多技巧不通过项目这样比较大的历练是用不上的。千锋官网每日更新最新软件开发基础知识内容,巩固日常学习中的基础技能。更有免费的软件开发视频教程帮助学员快速学习。 千锋教育就有线上免费的软件开发公开课,。
Web前端培训多长时间,只能说简单入门在五到六个月,真正要达到精通级别的话,需要天赋跟经验的积累。正所谓,一入前端深似海,从此回首无边界。活到老,学到老。只要步入了前端开发你就会发现,前端真的是要一直不停的学,不停的学。千锋教育集团目前已与国内4000多家企业建立人才输送合作,与500多所大学建立实训就业合作,每年为各大企业输送上万名移动开发工程师,每年有数十万名学员受益于千锋教育组织的技术研讨会、技术培训课、网络公开课及免费教学视频。
srcElement 是Dom事件中的事件最初指派到的元素。
比如有一个div,里面有一个按钮。你响应div的onclick事件,但实际上,你单击的只是它内部的按钮,那么,srcElement指向的,就是那个按钮。
srcElement只在IE中有效。
在Opera系列浏览器中对应的属性是target
给你一个IE下使用的例子。
!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" ""
html xmlns=""
head
title无标题页/title
script type="text/javascript"
function onLoad()
{
document.getElementById( "myDiv" ).attachEvent( "onclick", on_myDivClick );
}
function onUnLoad()
{
document.getElementById( "myDiv" ).detachEvent( "onclick", on_myDivClick );
}
function on_myDivClick( e )
{
if( !e ) e = window.event;
alert( "event: " + e.type + ", fromElement = " + e.srcElement.id );
}
/script
/head
body onload="onLoad()" onunload="onUnLoad()"
div id="myDiv"
input type="button" id="btn1" value="button1" /
input type="button" id="btn2" value="button2" /
/div
/body
/html
首先我们来定义LockingPtr用到的Mutex类的骨架:
class Mutex
{
public:
void Acquire();
void Release();
...
};
为了能使用LockingPtr,你要用你操作系统用到的数据结构和基本函数来实现Mutex。
LockingPtr用受控的变量的类型来作为模板。举例来说,如果你想管理一个Widget,你使用一个LockingPtrWidget,这样你可以用一个类型为volatile Widget的变量来初始化它。
LockingPtr的定义非常简单。LockingPtr实现一个相对简单的smart pointer。它目的只是把一个const_cast和一个临界区集中在一起。
Template typename T
Class LockingPtr {
Public:
//构造/析构函数
LockingPtr(volatile T obj, Mutex mtx)
: pObj_(const_castT*(obj)),
pMtx_(mtx)
{ mtx.Lock(); }
~LockingPtr()
{ pMtx_-Unlock(); }
//模拟指针行为
T operator*()
{ return *pObj_; }
T* operator-()
{ return pObj_; }
private:
T* pObj_;
Mutex* pMtx_;
LockingPtr(const LockingPtr);
LockingPtr operator=(const LockingPtr);
};
尽管简单,LockingPtr对写出正确的多线程代码非常有帮助。你应该把被几个线程共享的对象定义为volatile而且不能对它们使用const_cast——应该始终使用LockingPtr自动对象。我们通过一个例子来说明:
假设你有两个线程共享一个vectorchar对象
class SyncBuf {
public:
void Thread1();
void Thread2();
private:
typedef vectorchar BufT;
volatile BufT buffer_;
Mutex mtx_; //控制对buffer_的访问
}; 软件开发网
在一个线程函数中,你简单地使用一个LockingPtrBufT来取得对buffer_成员变量的受控访问:
void SyncBuf::Thread1() {
LockingPtrBufT lpBuf(buffer_, mtx_);
BufT::iterator I = lpBuf-begin();
For (; I != lpBuf-end(); I) {
...使用*i...
}
}
这些代码既非常容易写也非常容易懂——任何时候你需要用到buffer_,你必须创建一个LockingPtrBufT指向它。一旦你这样做,你就能够使用vecotr的所有接口。
非常好的事情是,如果你犯了错,编译器会指出来:
void SyncBuf::Thread2() {
//错误,不能对一个volatile对象调用begin()
BufT::iterator I = buffer_.begin();
//错误!不能对一个volatile对象调用end()
for (; I != lpBuf-end(); I) {
...使用*i...
}
}
你不能调用buffer_的任何函数,除非你要么使用一个const_cast要么使用LockingPtr。区别是LockingPtr提供了一个有序的途径来对volatile变量使用const_cast。
LockingPtr非常有表现力。如果你只需要调用一个函数,你能够创建一个无名临时LockingPtr对象并直接使用它:
Unsigned int SyncBuf::Size() {
Return LockingPtrBufT(buffer_, mtx_)-size();
}
回到基本类型
我们已经看到了volatile保护对象不被不受控制地访问时是多么出色,也看到了LockingPtr提供了多么简单和高效的方法来写线程安全的代码。让我们回到基本类型,那些加了volatile后行为与用户自定类型不同的类型
我们来考虑一个例子,多个线程共享一个类型为int的变量。
Class Count
{
public:
...
void Increment() { ctr_; }
void Decrement() { --ctr_; }
private:
int ctr_;
};
如果Increment和Decrement被不同线程调用,上面的代码片段是有问题的。首先,ctr_必须是volatile,其次,即使象 ctr_那样看上去是原子操作的函数实际上是一个三步操作。内存本身没有算术能力,当递增一个变量时,处理器:
* 读取那个变量到寄存器
* 在寄存器中增加值
* 把结果写回内存
这个三步操作叫做RMW(Read-ModifyWrite 读-改-写)。在执行一个RMW操作的“改”
操作时,为了让其他处理器访问内存,大多数处理器会释放内存总线。
如果那时另一个处理器对同一个变量执行一个RMW操作,我们就有了一个竟态条件;第二个写操作覆盖了第一个的结果。
你也能够用LockingPtr避免这种情况:
class Counter
{
public:
...
void Increment() { *LockingPtrint(ctr_, mtx_); }
void Decrement() { --*LockingPtrint(ctr_, mtx_); }
private:
volatile int ctr_;
Mutex mtx_;
};
现在代码正确了,但代码质量比较SyncBuf的代码而言差了很多。为什么?因为在Counter里,如果你错误地直接访问ctr_(没有先对它加锁)编译器不会警告你。如果ctr_是volatile, ctr_也能编译通过,但产生的代码明显是错误的。编译器不再是你的帮手了,只有靠你自己注意才能避免这样的竟态条件。
那你应该怎么做?简单地把你用到的基本数据包装为更高层次的结构,对那些结构用volatile。荒谬的是,尽管本来volatile的用途是用在内建类型上,但实际上直接这样做不是个好主意!
volatile成员函数
到目前为止,我们已经有了包含有volatile数据成员的类,现在我们来考虑设计作为更大对象一部分的类,这些类也被多线程共享。在这里用volatile成员函数有很大帮助。
当设计你的类时,你只对那些线程安全的成员函数加voaltile标识。你必须假定外部代码会用任何代码在任何时刻调用volatile函数。不要忘记:volatile等于可自由用于多线程代码而不用临界区,非volatile等于单线程环境或在一个临界区内。
例如,你定义一个Widget类,实现一个函数的两个变化——一个线程安全的和一个快的,无保护的。
Class Widget
{
public:
void Operation() volatile;
void Operation();
...
private:
Mutex mtx_;
};
注意用了重载。现在Widget的用户可以用同样的语法来调用Operation,无论你为了获得线程安全调用volatile对象的Operation还是为了获得速度调用常规对象的Operation。但用户必须小心地把被多线程共享的Widget对象定义为volatile。
当实现一个volatile成员函数时,第一个操作通常是对this用一个LockingPtr加锁。剩下的工作可以交给非volatile的对应函数:
软件开发网
void Widget::Operation() volatile
{
LockingPtrWidget lpThis(*this, mtx_);
LpThis-Operation(); //调用非volatile函数
}
总结
当写多线程程序时,你可以用volatile得到好处。你必须遵守下面的规则:
* 定义所有的被共享的对象为volatile。
* 不要对基本类型直接用volatile
* 当定义可被共享类时,使用volatile成员函数来表示线程安全。
如果你这样做,而且如果你使用那个简单的返型组件LockingPtr,你能够写出线程安
全的代码而不用更多考虑竟态条件,因为编译器能为你留心,会为你主动指出你错误的地方。
我参与的几个使用volatile和LockingPtr的计划获得很好的效果。代码清晰易懂。我记得碰到几处死锁,但我情愿遇到死锁也不要竟态条件,因为死锁调试起来容易得多。事实上没有遇到任何问题是关于竟态条件的。
学习javascript没HTMl基础有点难度,建议你先熟悉html再学习。
JavaScript简称JS,之前的基础就是HTML,HTML这门课程如果入门的话不是很难,刻苦点一月到两月就能搞定,有HTML基础的话,只要继续刻苦一个月左右JS就能入门,但是想学到高深那就不容易了,js入门后在继续学可以说也是有些难度的。总之先掌握HTML,这是一个基础,正如你说话要先从aoe开始一样,HTML也很容易学的
HTML推荐书籍:深入浅出HTML和CSS
JS推荐书籍:《javascript入门经典》
这些书籍可以帮助你怎么学习,其实不止看书,你也可以看看视频,多看视频讲解学习可以让你少走很多弯路,节省不少时间。遇见问题,常百度一下,现在百度只有你想不到的,没有你查不到的,没有你要的答案,也能查到相关的,何况可以提问嘛……
人就是在不断的问题中解决问题,发现新的问题,继续解决问题,这样自己的自学能力和技术能够得到很大的提升,关键就是不懂一定马上问,千万不要随便拖,这样进步才叫快……
还有补充一下,学习重在实践,因为只有实践你才能更好的发现自己的问题,一个问题解决了,一次不记得,下次继续做的时候再手打一次,但是别抄之前自己写过的代码,除非你觉得自己这段代码已经掌握了,这样为了节省时间才抄,否则还是练练手最好,,万变不离其宗——熟能生巧……
如果你精通了,那就好办了,一个网站可能就被你开发出来,然后就不愁找不到好工作了,至于你认为学到什么地步算精通,这你自己在学习中就可以感受到自己的能力,说的够多了,一时说不完,就这样,最后祝你成功,嘎嘎嘎嘎……