作为一个前端开发人员,JS是我们行走江湖吃饭的家伙。基本上一个前端人员能值多少大洋,就看JS了。虽然各种框架层出不穷,但是归根结底学好原生JS才是硬道理。

  学习任何新东西其实都遵循 10000 小时成才定律,只要付出时间,就会有收获。人与人的不同只是收获的多少不同。关于天赋问题,我们确实要承认某些人在某些领域确实比其他人厉害。但大部分人其实都是普通人,不需要天赋,只需要通过时间的简单堆积就可以混口饭吃。

  弹钢琴能到郎朗那个级别的人是少数了,多数艺术生都普普通通,毕业出来混个钢琴老师当当,办个培训学校赚点钱娶媳妇儿生孩子,最多写本书什么的。只有投入足够多的时间,你发现某些人确实比你厉害,这个时候才适合讨论天赋问题。所以,不要自我否定,才是真正的成长的开始。

  咱们言归正传吧。

  一,JavaScript的组成

  JavaScript主要由以下3部分组成:

  ECMAScript:解释器、翻译

  DOM:Document Object Model(文档对象模型)

  BOM:Browser Object Model(浏览器对象模型)

  ECMAScript类似于翻译的角色,将编写好的可读性高的代码翻译成计算机可以识别的二进制代码,并将计算机反馈回来的信息翻译给我们。ECMAScript是JS的核心,通常称为:解释器。

  ECMAScript为JS提供了最基本的功能,但这些功能是十分有限的,如何能让JS具有编写网页代码的能力呢?此时我们就要用到DOM了。DOM中的Document(文档)其实就是HTML文档,并且DOM还赋予了JS操作HTML的能力。在JS里DOM是以document的形式展现的。

  BOM使得JS拥有了操作浏览器的能力,在JavaScript当中BOM以window的形式存在,有了BOM,JS就拥有了类似弹窗,关闭窗口,复制内容到剪贴板等与浏览器相关的功能。

  从兼容性的角度来看的话,ES(ECMAScript)基本上不存在兼容性问题,DOM有一些操作上的不兼容,而BOM完全不兼容,所以尽可能避免使用BOM,这样可以省去很多的麻烦。

  二,变量类型

  首先说变量,从字面上理解就是可以变化的量,放到编程语言里面,就是可以被赋值改变的量。和变量对应的就是常量,我们经常遇到的比如,10,20这样的不能改变的数字,就是常量,一个确定的值。不能被赋值也不能被改变。

  在JS中我们把变量分为了多种类型。

var a = 1024;
alert(typeof a); var a = 'cos';
alert(typeof a); var a = true;
alert(typeof a); var a = function (){ alert('cos'); }
alert(typeof a); var a = document;
alert(typeof a);

  typeof 是一个一元运算,放在一个运算数之前,运算数可以是任意类型。它返回值是一个字符串,该字符串说明运算数的类型。

  我们可以通过typeof返回变量类型,那么上面的例子的输出结果,依次为:number(数值),string(字符串),boolean(布尔),function(函数),object(对象)。在这5中基础数据类型之外,JS还存在一种叫undefined的类型,一般存在于如下两种情况:

  alert(typeof b);

  变量b没有进行过定义,所以JS返回的数值类型为undefined(未定义的)。

  var b;

  alert(typeof b);

  这时,虽然我们定义了变量b,但在JS里,变量的类型只取决于变量内存的值,而变量b内没有值,因此它的数据类型依然是undefined。

  JS没有限制变量的数据类型,显得更加灵活,但如果一个变量不停地更改类型,会显得非常的混乱。所以同一个变量,最好只存放一种类型的数据。

  三,变量类型的转换

  变量不仅有类型,而且可以进行类型之间的转换。如果某个数据的类型不符合我们的需求,那么就需要用到数据类型的转换。我们一起举个‘栗子’:

  在网页中添加两个文本框和一个按钮,并希望点击按钮后文本框中的数字可以相加。这个功能看起来很简单,如果直接写的话,因为textbox中value的属性是以字符串形式返回给JS的,这就导致输入的两个数字最后会被当做字符串相加而不是数值。这时候,我们就需要将字符串转换为数字。

  将字符串转化为数字的方法为parseInt()。

  这是关于parseInt()的一个例子:

  var a = '1024'; alert(parseInt(a)+1);

  这里我们将a定义为了字符串,但是通过parseInt转化后得到了数值类型的数据,所以输出结果为1025。需要注意的是,parseInt是从左到右依次扫描字符串,一旦发现不是数字的字符,就立即停止工作,并将前面的字符通过数值类型返回,所以下面三种情况的返回结果依次为1024,1024,NaN:

var a = '1024px';
var b = '1024px24';
var c = 'abc';
alert(parseInt(a));
alert(parseInt(b));
alert(parseInt(c));

  这里的 NaN 是Not a Number的简写,简言之就是JS解析不出数字时会返回这个结果。

  所以,我们这个案例可以通过如下代码完成:

<script>
    window.onload=function ()      
{      
var oTxt1=document.getElementById('txt1');      
var oTxt2=document.getElementById('txt2');      
var oBtn=document.getElementById('btn1');      
oBtn.onclick=function ()      
{      
alert(parseInt(oTxt1.value)+parseInt(oTxt2.value));      
};      
};
</script>
<body>
    <input id="txt1" type="text" />
    <input id="txt2" type="text" />
    <input id="btn1" type="button" value="求和" />
</body>

  运行结果:

  这里有一个问题,我们并没有对文本框进行任何限制,当用户向文本框输入的是字母而不是数字的时候,程序是不能正常执行的。所以,这时候需要判断一下对文本框输入值通过 parseInt 方法转换出来的结果是不是 NaN,如果是NaN,就说明用户输入某个值或者这两个值不是数字,此时需要返回给用户一个提示。

  那么问题来了,在JS里,NaN十分的奇葩:

  var a=parseInt('abc');

  var b=parseInt('def');

  alert(a==b);

  此时,a和b的值都是NaN,但这个程序的执行结果居然是false,这告诉我们在JS里NaN和NaN是不相等的。换言之,判断结果是不是NaN,不能通过==进行比较。好在天无绝人之路,JS提供了一个函数:isNaN(),用于检测一个变量是否为NaN。

  现在我们来看:

  输入字母的时候效果如下:

  通过 if 进行判断,如果用户有输入的不是数字,则弹出与之对应的错误提示框;如果输入的两个值都没有错误,将会弹出正确答案。

  那么使用parseInt转换小数,会怎么样呢?

  var a='3.5';

  alert(parseInt(a));

  输出结果为3。对于parseInt而言,转换出来的数字如果是小数,就会舍去小数部分,只保留整数部分。

  如果我们需要用到小数的话,请使用parseInt的兄弟——parseFloat,这两者在使用方法上没有任何区别,你照猫画虎的试试看。当你不知道转换出来的数值是整数还是小数的时候,请优先选择使用parseFloat,此时即便转换前的变量为整数也不会出现数值缺损。

  在我们刚才所讲的类型转换中,明确地告知了计算机我们想要对数据类型进行转换,我们将这种方法称为显式类型转换(也可以理解为:强制转换)。同样,还有一种转换类型的方式被我们称为隐式类型转换。隐式类型转换最简单的例子如下:

  var a=5;

  var b='5';

  alert(a==b);

  理论上来讲的话,二者数据类型不相同,输出结果应该为flase。但是浏览器给出的答案是true。请和下面的例子做一个对比:

  var a=5;

  var b='5';

  alert(a===b);

  此时,返回的答案变成了false。那么问题来了,==和===二者之间存在什么区别呢?

  对于==运算符来说,它在比较之前会先把二者的数据类型转换为一致;而 === 运算符(全等运算符)不转换类型,直接比较。在不转换类型的情况下,a和b肯定是不相等。由此可知,在比较a==b时,并没有明确告知计算机我们想要对a或b的类型进行转换,但是计算机自己却偷偷进行了转换,这就是我们所讲的隐式类型转换。除开该例子之外,还存在另一种隐式转换的情况:

  var a='12';

  var b='5';

  alert(a-b);

  如果这里是a+b,计算机就会默认是字符串相加(拼接)而弹出125。但是如果是a-b的话,计算机会在做减法之前进行隐式转换成数值类型,我们就得到答案7。

  为什么加法不会进行隐式转换而减法会?因为在JS中+运算符本身具备字符串拼接和数字相加这两个功能,如果+识别为字符串拼接,一步即可完成计算,直接拼接即可;但是如果识别为数字相加,就需要两步才可以完成计算,即:先转换类型,再相加。对于计算机而言,一定会选择步骤更少的路径,所以说加法不会进行隐式转换。而在JS中,-运算符只有数字相减的功能,此时JS不得不进行隐式转换。

  四,变量作用域

  变量作用域指的是变量可以起作用的范围。

  

function aaa(){
  var a=12;
  }
  function bbb(){
  alert(a);
  }
  aaa();
  bbb();

  运行这个程序,在bbb函数内会出现变量a没有被定义的报错。事实上,a确实没有被定义,因为在aaa中定义的a是局部变量,而局部变量,只能在定义它的函数里面使用。和局部变量相对的一个概念是全局变量。

  var a;

  function aaa(){

  a=12;

  }

  function bbb(){

  alert(a);

  }

  aaa();

  bbb();

  这个例题当中的a被声明在所有函数的外面,这样的变量是全局变量,可以在任何地方使用,所以能够正常弹出12。

  五,闭包

  关于闭包的概念,我建议你现阶段先不用深究,如果很感兴趣的话可以Google一下。咱们说过,局部变量只能在定义它的函数内使用。那么,有一种情况例外:

  function aaa(){

  var a=12;

  function bbb()

  {

  alert(a);

  }

  bbb();

  }

  aaa();

  当函数bbb被包含在函数aaa内时,程序可以成功运行。此种写法就被称为闭包。闭包有很多高级的应用,当然这些都是后话,我们慢慢学习。在闭包结构中,aaa称为父函数,bbb称为子函数。对于闭包而言,子函数可以使用父函数的局部变量。事实上,刚刚我们已经使用过闭包了,例如上面的求和函数。

  六,命名规范

  命名规范,即怎样给函数以及变量取名字。

  给函数和变量取名字和给你孩子取名字差不多,理论而言是可以随便取的,但实际应用中又不能显得太俗太low,否则可能会引起隔壁老王的不满。

  关于命名规范:

  可读性——容易看懂

  规范性——合乎规则

  可读性代表取名尽可能让人能看懂。要是代码通篇都是aaa,bbb,ccc这样的取名,又正好碰到程序比较庞大,此时阅读将是一件非常痛苦的事情。

  规范性表示JS有一个较为约定俗称的命名规则,大部分情况下采用匈牙利命名法或者类似方法,其原则为:

  类型前缀

  首字母大写

  JS中常见类型前缀:

  类型前缀一般表明了变量存储的类型,使我们一眼就能辨识变量当中存的是什么,其他人拿到代码的时候就不会胡乱更改数据类型,这样保证了代码的规范和更好的可读性。一般而言只有变量遵循前缀的规范,而函数则没有这个必要。

  当一个变量或者函数名由多个英文单词组成的时候,我们通常使用驼峰法命名,每个单词的首字母使用大写,例如oBtnUserLogin,这种命名方式可以更清晰地判断变量的含义。

【JavaScript从入门到放弃】JS基础-01的更多相关文章

  1. 初学JavaScript从入门到放弃(一)JavaScript介绍、变量、数据类型

    一.JavaScript介绍 1.JavaScript:轻量级的客户端脚本语音 2.目前js已经不仅仅是客户语音,基于NODE可以做服务器端程序,所以Javascript是全栈编程语音 3.js及部分 ...

  2. js基础01

    常见的五大浏览器:chrome firfox ie opera safari 浏览器的解析器会把代码解析成用户所能看到的东西 www.2cto.com/kf/201202/118111.html浏览器 ...

  3. JavaScript 从入门到放弃(二)模块化工具requirejs

    入门教程: 1.JS模块化工具requirejs教程(一):初识requirejs 2.JS模块化工具requirejs教程(二):基本知识 描述 这几天在使用github最活跃的基于bootstra ...

  4. JavaScript 从入门到放弃(一)事件委托和使用innerHTML添加元素

    一.使用事件委托 一个简单的需求,比如想给ul下面的li加上点击事件,点击哪个li,就显示那个li的innerHTML.这个貌似很简单!代码如下! <!DOCTYPE html> < ...

  5. QML 从入门到放弃

    发现了一个问题: QQuickView only supports loading of root objects that derive from QQuickItem. If your examp ...

  6. 二、JavaScript语言--JS基础--JavaScript入门篇

    1.如何插入JS 使用<script>标签在HTML网页中插入JavaScript代码.注意, <script>标签要成对出现,并把JavaScript代码写在<scri ...

  7. Web3D编程入门总结——WebGL与Three.js基础介绍

    /*在这里对这段时间学习的3D编程知识做个总结,以备再次出发.计划分成“webgl与three.js基础介绍”.“面向对象的基础3D场景框架编写”.“模型导入与简单3D游戏编写”三个部分,其他零散知识 ...

  8. D3.js从入门到“放弃”指南

    前言 近期略有点诸事不顺,趁略有闲余之时,玩起D3.js.之前实际项目中主要是用各种chart如hightchart.echarts等,这些图形库玩起来貌都是完美的,一切皆可配置,但几年前接触了D3之 ...

  9. javascript基础01

    javascript基础01 Javascript能做些什么? 给予页面灵魂,让页面可以动起来,包括动态的数据,动态的标签,动态的样式等等. 如实现到轮播图.拖拽.放大镜等,而动态的数据就好比不像没有 ...

随机推荐

  1. Python基础学习(day1)

    一.Python几点使用规范: 1.关于引号的使用规范 (1)字符串中含有单引号,则使用双引号外扩 print("It's ok") (2)字符串中含有双引号,则使用单引号外扩 p ...

  2. C#第十节课

    类 using System;using System.Collections.Generic;using System.Linq;using System.Text;using System.Thr ...

  3. 图片base64格式转为file文件类型上传方法

    日常使用文件上传方式,都是通过input type='file'的文件选择框进行文件上传.但是会通过其他交互方式等到图片的base64格式进行上传.具体情况如下示意: 在项目开发中,需要进行照片采集, ...

  4. Django-Python3-Celery 异步任务/定时任务

    1. 目录结构 2. setting设置: 3. project/project/celery.py 4. project/project/__init.py 5.任务分配 6. 代码实现 View ...

  5. IMSI MCC MNC概念

    TelephonyManager telManager = (TelephonyManager) getSystemService(Context.TELEPHONY_SERVICE); /** 获取 ...

  6. Codeforces 947E Perpetual Subtraction (线性代数、矩阵对角化、DP)

    手动博客搬家: 本文发表于20181212 09:37:21, 原地址https://blog.csdn.net/suncongbo/article/details/84962727 呜啊怎么又是数学 ...

  7. VIM 使用 匹配替换命令配合表达式 实现 递增替换

    :let n=100 | g/while/s/\d/\=n / | let n=n+1 before 10 void *thread_function_1(void *arg) { 11 int i; ...

  8. SpringBoot支持AJAX跨域请求

    利用注解的方式解决AJAX请求跨域问题 1.编写一个支持跨域请求的 Configuration - 第一种方式 - CorsConfig.java import org.springframework ...

  9. Mycat分表分库

    一.Mycat介绍 Mycat 是一个开源的分布式数据库系统,是一个实现了 MySQL 协议的的Server,前端用户可以把它看作是一个数据库代理,用 MySQL 客户端工具和命令行访问,而其后端可以 ...

  10. CodeForces 453A 概率题

    Description Twilight Sparkle was playing Ludo with her friends Rainbow Dash, Apple Jack and Flutter ...