JS编码基础/JS函数/JS方法覆盖调用

自定义类

使用this关键字修饰的变量不再是局部变量,它是该函数的实例属性

<script>
        function Student(name, age, sex) {
            this.name = name;
            this.age = age;
            this.sex = sex;
        }
        let bb = new Student("胖子", 18, true);
        console.log(bb)
        let ss = bb.name + "," + bb.age + "," + (bb.sex ? '男' : '女');
        console.log(ss);
        //更加簡化的定義方式
        var pan = {};
        //添加屬性
        pan.name = "綠毛";
        pan.age = 12;
        pan.sex = false;
        console.log(pan);
    </script>
<script>
        function Person(name, age) {
            //实例对象每个实例都不同,可以通过new Person("",19).name的方式访问
            this.name = name; 
            //类属性,是类的所有实例公用,只能通过Person.nation的方式访问,
            //而不能使用new Person("yan",18).nation方式访问
            // Person.nation = "汉族";  
            Person.nation=age;
            var bb = 0;//局部变量,外面不能访问,类似局部函数
        }

        let p1=new Person("zhangsan","白族");//new Person;
        let p2=new Person("黃毛","蟲族");
        console.log(p1);
        console.log(p2);
        console.log(Person.nation);

        //注意:局部变量在函数执行完毕后销毁,全局变量在页面
        //关闭后销毁,函数内没有使用var声明的变量为全局变量
        //直接定义一个对象
        var p = {  //JSON格式定義
            //this.pp=function(){}可以用於function p(){}定義中
            pp: function () {
                for (var k = 0; k < 10; k++)
                    document.writeln("慢慢的走...");
            }
        }
        //调用方式
        p.pp();
    </script>

Js中的函数

函数就像java方法一样,这个函数可以被调用

定义一个函数时,系统也会创建一个对象,这个对象就是Function类的实例

定义一个函数时,这个函数通常都会附加给某个对象,作为对象的方法。没有明确指出将函数附加到哪个对象上时,该函数将附加到window对象上,作为window对象的方法。

<script>
        function ff1(){
            document.write('ff1()');
        }
        console.log(window);
        window.ff1();
    </script>

定义函数时也得到了一个与函数同名的类,该函数就是该类的唯一的构造器。

所以实际上函数有直接调用和使用new关键字调用两种方式

<script>
       function Student(){
           alert("Student");
       }
       //Student();直接調用
       new Student(); //將function定義當做構造器使用
</script>

js的运行机制

  • 在js中js引擎会优先解析var变量和function定义,在预解析完成后从上到下逐步进行
  • 解析var变量时会把值存储在执行环境中,而不会去赋值,值是存储作用!如alert(a);
    var a = 5;这时会输出undifiend,意思是没有被初始化没有被赋值。这并不是没有被定义,错误的意思
  • 在解析function时会把函数整体定义,这也就解释了为什么在function定义函数时为什么可以先调用后声明了!其实表面上看是先调用了,其实在内部机制中第一步实行的是把以function方式定义的函数先声明了!
<script>
        name="zhangsan";
        function ff(){
            alert(name);
            // var name=123;
            let name=999;
        }
        ff();
    </script>

ES6中箭头函数的调用

箭头函数表达式的语法比函数表达式更简洁,并且没有自己的this,arguments,super或 new.target。这些函数表达式更适用于那些本来需要匿名函数的地方,并且它们不能用作构造函数

(参数1, 参数2, …, 参数N) => { 函数声明 }

相当于:(参数1, 参数2, …, 参数N) =>{ return 表达式; }
(参数1, 参数2, …, 参数N) => 表达式(单一语句)

当只有一个参数时,圆括号是可选的:
(单一参数) => {函数声明}
单一参数 => {函数声明}

没有参数的函数应该写成一对圆括号。
() => {函数声明}

<script>
        //es5中:
        var x = 11;
        var obj = {
            x: 22,
            say: function () {
                console.log(this.x)
            }
        }
        obj.say(); //22

        //而在es6中
        var x = 11;
        var obj = {
            x: 22,
            say: () => {
                console.log(this.x);
            }
        }
        obj.say(); //11
    </script>
 <script>
        var bb = {
            pp: function () {
                console.log(this);  //this是Bb对象
            }
        }
        bb.pp();

        var obj = {
            pp: () => {
                console.log(this);//是window,而不是obj对象  [重点]
            }
            /*
            - 箭头函数不可以当作构造函数使用,也就是不能用new命令实例化一个对象,
            否则会抛出一个错误
            - 箭头函数的this是和定义时有关和调用无关,无论使用apply还是call都无
            法改变
            - 调用就是函数调用模式
            */
        }
        obj.pp();
    </script>
 <script>
        (() => {
            console.log(this)//window
        })()

        let arrowFun = () => {
            console.log(this)//window
        }
        arrowFun()

        let arrowObj = {
            arrFun: function () {
                (() => {
                    console.log(this)//arrowObj
                })()
            }
        }

        arrowObj.arrFun();
    </script>

原型对象

<script>
        function Student(){
            this.name="name";
            this.pp=function(){
                alert(this.name+"---"+age);
            }
            var age=100;  //只能在当前函数内部进行访问,其它地方不能访问,即使使用prototype原型
        }
        
        var s1=new Student();
        s1.abc=function(){
            alert("s1....abc");
        }
       
        Student.prototype.abc=function(){
            console.log(this.name);
            // console.log(age);因为age是临时变量
            return "ppppp";
        }
        var s2=new Student();
        // alert(s2.abc());
        s2.pp();
    </script>

外部读取局部变量

<script>
    function Student(){
        function abc(){
            return kk;
        }
        var kk=999;
        return abc;
    }

    var s=new Student();
    alert(s.kk);  //undefined
    alert(s());   //999
</script>

类基础定义

<script>
        function Student() { 
            this.toString=function(){
                return "xxxx";
            }
        }

        var s1 = new Student();
        s1.name = "胖子";
        s1.age = 19;
        // alert(s1);
        console.log(s1);
        //覆盖定义
        s1.toString=function(){
            return this.name+"---"+this.age;
        }
        console.log(s1.name + "---" + s1['name']);
        console.log(s1.toString());
        /*
        访问对象公开属性的方式有两种:
        - 对象名.属性名
        - 对象名['属性名']
        */
    </script>

局部变量和局部函数

在函数内部定义的变量称为局部变量,在函数外部定义的变量称为全局变量

局部函数是指在函数中定义的函数

<script>
        function ff3(){
            alert("ff3"+bb); 
            var bb=123;
        }
        ff3();
    </script>
    <script>
        var bb="abcd";
        function ff1(){
            var bb=999;
            alert("ff1"+bb);
        }
        ff1();
    </script>
    <script>
        function ff2(){
            alert("ff2"+bb);
        }
        ff2();
    </script>
<script>
        function nn1(){
            nn2();
            function nn2(){
                alert("nn2");
            }
            alert("nn1");
        }
        nn1();
        nn2();  //nn2只能在nn1的內部進行調用
    </script>
    <script>
         function nn3(){
            function nn4(){
                alert("nn4");
            }
            return nn4; //允許返回當前function中定義的內部function
        }
        nn3()(); //調用nn4();
    </script>
    <script>
        function outer(){
            function inner(){//局部函数
                document.writeln("内部函数1111<br/>");
            }
            document.writeln("测试局部函数.....开始");
            inner();
            document.writeln("测试局部函数.....结束");
        }
        //在全局函数outer中定义了一个局部函数inner,在outer中调用没有问题,但是在outer之外则无法访问
        outer();
    </script>

函数

js是一种基于对象的脚本语言,代码复用的范围是函数,函数可以独立存在。

函数的最大作用是提供代码复用,将需要重复使用的代码块定义为函数,提供更好的代码复用

编写JS的流程

布局:html+css 在写js之前必须保证有一个稳固的布局,这个布局本身不能有任何兼容问题

属性:确定要修改哪些属性 确定通过js修改哪些属性,例如display

事件:确定用户做哪些操作(产品设计)确定要在什么样的事件里修改,比如点击、移入移出

编写js:在事件中,用js来修改页面元素的样式

原始数据

<button onclick="ff()" id="btn1">隐藏</button>
    <script>
        function ff() {
            document.getElementById("div1").className = "bb1";
            document.getElementById("btn1").innerText = "显示";
            document.getElementById("btn1").onclick = dd;
        }
        function dd() {
            document.getElementById("div1").className = "bb2";
            document.getElementById("btn1").innerText = "隐藏";
            document.getElementById("btn1").onclick = ff;
        }
    </script>
    <style>
        .bb1 {
            display: none;
        }

        .bb2 {
            display: block;
        }
    </style>
    <label onmouseover="document.getElementById('btn1').style.display='block'"
        onmouseout="document.getElementById('btn1').style.display='none'">
        鼠标经过出现按钮</label>

定义函数的3种方式

三种方法的对比

  • 函数声明有预解析,而且函数声明的优先级高于变量
  • 使用Function构造函数定义函数的方式是一个函数表达式,这种方式会导致解析两次代码,影响性能。第一次解析常规的JavaScript代码,第二次解析传入构造函数的字符串

命名函数

function hello(name){
alert(‘欢迎您,’+name+",你好!");
}

在同一个script标签中允许先调用函数,然后再定义函数;在不同的script中要求必须先定义函数,然后再调用函数

 <script>
        h1("猴子");
        function h1(name) {
            alert('Hello ' + name + "!")
        }
        function h2(name) {
            alert('Hello ' + name + "!")
        }
    </script>
    <script>
        h2("胖子");
    </script>

定义匿名函数

定义匿名函数无需指定函数名,而是将参数列表紧跟在function关键字后

匿名函数有很好的可读性。注意js函数很特殊,即使可重复调用的代码块,也是一个Function实例

<script>
        var f=function(name){
            document.writeln('匿名函数!<br/>');
            document.writeln('你好,'+name);
        };
        f('yanjun');

        //語法錯誤
        /*
        function(){
            alert('ddddd');
        }
        */
    </script>

使用Function类匿名函数

<script>
        var f=new Function('name',"document.writeln('Function定义的函数<br/>');"
      + "document.writeln('你好'+name);");
        f("小明");
    </script>

方法覆盖

看代码

<script>
    function Student(){  //构造器
        this.name="猴子";
        this.sleep=function(){
            return "我要找母猴子";
        }
    }
    var a=new Student;
    console.log(a.name);
    //在对象中进行方法覆盖
    a.sleep=function(){
        return "我爱母猴子";        
    }
    console.log(a.sleep());
    var b=new Student;
    console.log(b.sleep());
    console.log(Student.prototype)
    //通过原型对象可以新增加方法,但是不能实现方法的覆盖定义
    Student.prototype.sleep1=function(){
        return "猴子爱桃子";
    }
    console.log(a.sleep());
    var c=new Student();
    console.log(c.sleep());
    console.log(Student.prototype)
    //js函数不支持重载
</script>

调用函数

调用函数的四种方式

作为一个函数去调用【函数名()】(函数作为全局对象调用,会使this的值成为全局对象,使用window对象作为一个变量,容易造成程序崩溃!) ,例如alert(’’)

函数作为方法调用:(函数作为对象的方法调用,会使this的值成为对象的本身!),例如window.alert(’’)

使用构造函数调用函数:(构造函数中的this指向当前对象) new Date()

作为函数方法间接调用函数pp()();

函数直接调用

<script>
        function ff1() {
            this.name = "abc";
            console.log(this);
        }
        // console.log(this)
        // ff1();
    </script>

对象方法调用

<script>
        var objList = {
            name: 'methods',
            getSum: function () {
                console.log(this) //objList对象
            }
        }
        objList.getSum()
        console.log(this);
    </script>

构造器调用

<script>
        function Person() {
            console.log(this); //指向构造函数Person
        }
        var personOne = new Person();
    </script>

间接调用

利用call和apply来实现,this就是call和apply对应的第一个参数,如果不传值或者第一个值为null、undefined时this指向window

<script>
        function foo() {
            console.log(sss)
            console.log(this);
        }
        foo.apply('我是apply改变的this值');//我是apply改变的this值
        foo.call('我是call改变的this值');//我是call改变的this值

        function f1() {
            alert("f1.....")
        }
        f1("abcd");
    </script>
<script>
        window.color = 'red';
        document.color = 'yellow';
        var s1 = { color: 'blue' };
        function changeColor() {
            console.log(this.color);
        }
        //通过第一个参数用于指定所调用函数中的this是谁
        //changeColor()
        changeColor.call();         //red (默认传递参数)  
        //window.changeColor();
        changeColor.call(window);   //red
        //document.changeColor();
        changeColor.call(document); //yellow
        //this.changeColor();
        changeColor.call(this);     //red
        //s1.changeColor();
        changeColor.call(s1);       //blue,劫持了函数中的this,使this为s1对象
    </script>

以apply方法调用
call调用函数时必须在括号中详细列出每个参数
apply动态调用函数时,可以在括号中以arguments代表所有的参数

call和apply用法
间接调用函数,改变作用域的this值
劫持其他对象的方法

 <script>
        function f9(){
            console.log(this.getYear());
        }
        f9.call(new Date);
    </script>

因为javascript中没有class类,所以有人把类也称为原型对象,因为这两个概念从在编程中发挥的作用看都是一个意思,为了统一叫法,这里就统一叫类

闭包

函数定义在另外一个函数内部可以达到限制访问的目的

<script>
       function func() {
           var num = 0;            //声明局部变量:num

           function f() {          //嵌套函数,在作用域里
               console.log(++num)
           }
           return f;             //调用嵌套函数f,并将f的执行结果返回
       }

       var ff = func();
       window.ff();                //输出:1
       ff();                       //输出:2
       ff();                       //输出:3
   </script>

函数对象可以通过作用域链相互关联起来,函数体内部的变量都可以保存在函数作用域内。

通常说的闭包是当一个函数嵌套另一个函数,外部函数将嵌套函数对象作为返回值返回的时候,我们把这种情况称为闭包


当一个函数func()创建后,它保存了一个作用域链,并且作用域链会被函数func()中的作用域中可访问的数据对象num填充

执行此函数func()时会创建一个称为“运行期上下文(execution context)”的内部对象,运行期上下文定义了函数执行时的环境。并且运行期上下文对应自己的作用域链,同时它的作用域链

初始化为当前运行函数func()的[[Scope]]所包含的对象,然后执行环境会创建一个活动对象(call object),用来报讯局部变量,并把这个对象添加至作用域链[[Scope]]中。假如不存在嵌套函数,也没有其他引用的时候,活动对象就会被当做垃圾回收掉。但是这里有嵌套函数f(),并将函数f()作为返回值返回时,就会又一个外部引用指向这个嵌套函数f(),活动对象就不会当做垃圾回收掉,并且活动对象指向的变量所绑定的对象也不会被回收。

在实际开发中,闭包主要是用来封装变量实现公有私有变量,收敛权限.

优点:

  • 变量长期驻扎在内存中
  • 避免全局变量的污染
  • 私有成员的存在

缺点:

  • 因为不会被GC回收,所以常驻内存,会增大内存的使用量,使用不当会造成内存泄露。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
JavaScript调用PHP函数,常用的方法是通过AJAX技术实现。AJAX全称为Asynchronous JavaScript and XML,是一种无需刷新页面就能实现异步数据交互的技术。AJAX技术的实现依赖于XMLHttpRequest对象,它是一种浏览器内置的JavaScript对象,能够与服务器建立HTTP请求并接收服务器返回的数据。 在使用AJAX调用PHP函数时,需要在JavaScript中创建一个XMLHttpRequest对象,然后利用它来向服务器发送请求。具体的步骤如下: 1. 创建XMLHttpRequest对象 在JavaScript中创建一个XMLHttpRequest对象,可以通过以下代码实现: var xhr = new XMLHttpRequest(); 2. 定义回调函数 由于AJAX是异步的,因此需要定义一个回调函数,来处理服务器返回的数据。回调函数一般被设置为XMLHttpRequest对象的onreadystatechange属性。在回调函数中,可以利用JavaScript来处理服务器返回的数据。 xhr.onreadystatechange = function() { if (xhr.readyState == 4 && xhr.status == 200) { // 在这里处理服务器返回的数据 } }; 3. 向服务器发送请求 AJAX技术可以使用GET和POST两种方式向服务器发送请求。GET方式将请求数据放在URL中,而POST方式则将请求数据放在请求体中。这里以POST方式为例。 xhr.open("POST", "php_function.php", true); xhr.setRequestHeader("Content-type", "application/x-www-form-urlencoded"); xhr.send("param1=value1&param2=value2"); 其中,xhr.open()方法用于打开一个HTTP请求,其中第一个参数是请求方式(POST),第二个参数是请求的URL地址,第三个参数表示是否异步。xhr.setRequestHeader()方法用于设置HTTP请求头信息,其中Content-type属性指定请求体的格式。xhr.send()方法用于向服务器发送请求体数据。 4. 在PHP中定义函数 最后,需要在PHP文件中定义一个函数,来处理前端的请求。这个函数可以接收前端发送的数据,并返回处理结果。 function php_function() { $param1 = $_POST['param1']; $param2 = $_POST['param2']; // 在这里处理参数,并返回结果 } 以上就是JavaScript调用PHP函数的大致步骤。在实际应用中,还需要注意一些细节问题,比如数据的编码方式,请求的安全性等。同时,AJAX技术也有自己的局限性和缺点,需要结合实际情况选择合适的技术方案。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值