前端面试题---JS

2 篇文章 0 订阅
2 篇文章 0 订阅

更多前端企业面试题可查看小程序–小狼学前端
在这里插入图片描述

1.JS数据类型有哪些?

答案解析:
	(1)在ES5的时候,我们认知的数据类型确实是 6种:Number、String、Boolean、undefined、object、Null <br>
	(2)ES6 中新增了一种 Symbol 。这种类型的对象永不相等,即始创建的时候传入相同的值,可以解决属性名冲突的问题,做为标记。<br>
	(3)谷歌67版本中还出现了一种 bigInt。是指安全存储、操作大整数。<br>
	(4)所以:准确来说目前JS数据类型总共有8种!<br>
		Number、String、Boolean、undefined、object、Null 、Symbol、bigInt<br>
	(5)按照类型来分有基本数据类型和引用数据类型:<br>
		基本数据类型:String、Number、Boolean、Null、Undefined、Symbol、BigInt<br>
		引用数据类型:Object【Object是个大类,function函数、array数组、date日期...等都归属于Object】<br>

2.什么是“use strict”,好处和坏处?

答案解析:
	(1)“use strict”:表示使用严格模式, "严格模式"是一种在JavaScript代码运行时自动实行更严格解析和错误处理的方法。<br>
	(2)优点<br>
		● 消除Javascript语法的一些不严谨之处,减少一些怪异行为;<br>
		● 消除代码运行的一些不安全之处,保证代码运行的安全;<br>
		● 提高编译器效率,增加运行速度;<br>
		● 为未来新版本的Javascript做好铺垫	<br>
	(3)缺点<br>
		● 严格模式改变了语义。依赖这些改变可能会导致没有实现严格模式的浏览器中出现问题或者错误<br>
		● 严格模式的限制<br>
   		 	1)变量必须声明后再使用<br>
    		2)在使用默认参数的函数中的参数不能有同名属性,否则报错,在同一作用域中不能有同名参数<br>
    		3)禁止this指向全局对象<br>
    		4)不能删除变量delete prop,会报错,只能删除属性delete global[prop]<br>

3.数据类型检测的方式有哪些?

答案解析:
	(1)typeof检测,返回的是对应类型的字符串,这个方法常用于检测基本数据类型,检测null和引用数据类型不准确;<br>
	(2)instanceof检测,返回的是布尔值,只要是基本数据类型就是false,只要是引用数据类型,并且右边是Object就是true,可以很好区分是哪一大类型<br>
	(3)constructor 返回的是构造函数,可以检测基本数据类型和引用数据类型, 但是有一定缺陷,就是原型可以被修改<br>
	(4)Object.getPrototypeof() 返回的是原型<br>
 	(5)Object.prototype.toString.call() 检测 任何数据类型都可以检测<br>

4.null和undefined的区别?

答案解析:
	(1)null 和 undefined 都是js语言的基础数据类型, 都是原始值类型<br>
	(2)undefined是表示变量声明过但并未赋过值,它是所有未赋值变量默认值;null表示一个变量将来可能指向一个对象,一般用于主动释放指向对象的引用。<br>
	(3)null == undefined //true <br>
		null === undefined //false<br>
		typeof null // 'object'<br>
		typeof undefined // 'undefined'	<br>

5.数组pop(), push(), unshift(), shift()的区别

答案解析:
	(1)push() 方法将一个或多个元素添加到数组的末尾,并返回该数组的新长度。 <br>
	(2)shift() 方法从数组中删除第一个元素,并返回该元素的值。此方法更改数组的长度。 <br>
	(3)unshift() 方法将一个或多个元素添加到数组的开头,并返回该数组的新长度。 <br>
	(4)pop() 方法从数组中删除最后一个元素,并返回该元素的值。此方法会更改数组的长度。 <br>

6.console.log(0.1 + 0.2),如何让其等于0.3

答案解析:
	0.1+0.2的结果不是0.3,而是0.3000000000000000004,JS中两个数字相加时是以二进制形式进行的,当十进制小数的二进制表示的有限数字超过52位时,在JS里是不能精确储存的,这个时候就存在舍入误差。<br>
    如何实现0.1+0.2=0.3?<br>
(1).ES6提供的Number.EPSILON方法, Number.EPSILON实际上是 JavaScript 能够表示的最小精度,等于 2 的-52 次方,误差如果小于这个值,就可以认为已经没有意义了,即不存在误差了。<br>
	function numbersequal(a,b){ <br>
  		return Math.abs(a-b)<Number.EPSILON;<br>
	}<br>
	var a=0.1+0.2, b=0.3;<br>
	console.log(numbersequal(a,b)); //true<br>
(2)把计算数字 提升 10 的N次方 倍 再 除以 10的N次方。N>1.<br>
	let a = (0.1 * 100 + 0.2 * 100) / 100<br>
	let b = 0.3<br>
	console.log(a === b);//true <br>

7.=的区别?

答案解析:
	(1)"==“叫做相等运算符,”==="叫做严格运算符。<br>
	(2)==,等同的意思,两边值类型不同的时候,要先进行类型转换为同一类型后,再比较值是否相等。<br>
      ===,恒等的意思,不做类型转换,类型不同的结果一定不等。<br>
	(3)"==“表示只要值相等即可为真,而”==="则要求不仅值相等,而且也要求类型相同。<br>

8.事件冒泡和事件捕获到底有何区别?

答案解析:
	 事件冒泡和事件捕获这两个概念都是为了解决页面中事件流(事件发生顺序)的问题。<br><br>
	(1)事件冒泡	<br>
		事件冒泡:事件会从最内层的元素开始发生,一直向上传播,直到document对象。<br>
	(2)事件捕获<br>
		事件捕获:与事件冒泡相反,事件会从最外层开始发生,直到最具体的元素。<br>
	(3)addEventListener方法<br>
		element.addEventListener(event, function, useCapture)<br>
		第一个参数是需要绑定的事件,第二个参数是触发事件后要执行的函数。而第三个参数默认值是false,表示在事件冒泡的阶段调用事件处理函数,如果参数为true,则表示在事件捕获阶段调用处理函数。<br>

9.typeof NaN的结果是什么?

答案解析:
	NaN指不是一个数字(not  a  number),NaN是一个"警戒值"(sentinel value,有特殊用途的常规值),用于指出数字类型中的错误情况,即执行数学运算没有成功,这是失败后的返回结果; <br>
    typeof  NaN;  //  number<br>
注意: NaN比较特殊,他自己不等于自己 即 NaN ===  NaN ; //false<br>

10.什么是typescript?

答案解析:
	(1)它是JavaScript的一个超集,而且本质上向这个语言添加了可选的静态类型和基于类的面向对象编程。<br>
	(2)TypeScript扩展了JavaScript的语法,所以任何现有的JavaScript程序可以不加改变的在TypeScript下工作。TypeScript是为大型应用之开发而设计,而编译时它产生 JavaScript 以确保兼容性。<br>

11.什么是模块化编程?

答案解析:
	(1)模块化编程是指将大型、笨拙的编程任务分解为单独的、更小更易于管理的子任务或模块的过程。然后可以像构建块一样拼凑单个模块以创建更大的应用程序。<br>
     优点:简单性、可维护性、可重用性<br>
     函数、模块和包都是js中用于促进代码模块化的构造。<br>

12.简述javascript原型、原型链?

答案解析:
	(1)函数可以有属性。 每个函数都有一个特殊的属性叫作原型prototype,也就是当创建一个函数,浏览器会自动分配一个对象,这个对象就是原型对象;<br>
	(2)每个实例对象(object)都有一个私有属性(称之为 __proto__)指向它的构造函数的原型对象(prototype)。该原型对象也有一个自己的原型对象(__proto__),层层向上直到一个对象的原型对象为 null。根据定义,null 没有原型,并作为这个原型链中的最后一个环节,那么产生的这样的一个链式关系,我们称为原型链<br>

13.解释javascript中的作用域和作用域?

答案解析:
	(1)作用域是当前的执行上下文,即变量或引用的有效范围,值和表达式在其中“可见”或可被访问。如果一个变量或表达式不在当前的作用域中,那么它是不可用的。<br>
    (2)作用域形成堆叠成层次结构,即多个作用域之间形成嵌套关系,那么子作用域可以访问父作用域,反过来则不行。

14.JavaScript 的作用域?

答案解析:
	(1)JavaScript 的作用域分以下三种:<br>
		-1.全局作用域:脚本模式运行所有代码的默认作用域<br>
		-2.模块作用域:模块模式中运行代码的作用域<br>
		-3.函数作用域:由函数创建的作用域<br>
     (2)此外,用 let 或 const 声明的变量属于额外的作用域:<br>
		块级作用域:用一对花括号(一个代码块)创建出来的作用域<br>

15.变量声明提升?

答案解析:
	变量提升被认为是,Javascript 中执行上下文(特别是创建和执行阶段)工作方式的一种认识。<br>
    例如,从概念的字面意义上说,“变量提升”意味着变量和函数的声明会在物理层面移动到代码的最前面,但这么说并不准确。实际上变量和函数声明在代码里的位置是不会动的,而是在编译阶段被放入内存中。<br>
	变量提升也适用于其他数据类型和变量。变量可以在声明之前进行初始化和使用。但是如果没有初始化,就不能使用它们。 译者注:函数和变量相比,会被优先提升。这意味着函数会被提升到更靠前的位置。 JavaScript 只会提升声明,不会提升其初始化。<br>

16.call()和apply()以及bind()三个方法的区别?

答案解析:
	(1)call()方法<br>
    	-1.实现方法借用,立刻调用当前函数<br>
        -2.改变当前this指向<br>
        -3.参数一个一个方式进行传递<br>
    (2)apply()方法<br><br>
    	-1.实现方法借用,立刻调用当前函数<br>
        -2.改变当前this指向<br>
        -3.参数以数组或者伪数组进行传递<br>
    (3)bind()方法<br>
    	-1.实现方法借用,返回一个新的函数,不能立刻调用函数<br>
        -2.改变当前新的函数this指向<br>
        -3.参数一个一个方式进行传递<br>

17.谈谈this对象的理解?

答案解析:
	this值是当前执行上下文(global、function 或 eval)的一个属性,在非严格模式下,总是指向一个对象,在严格模式下可以是任意值。<br>
    与其他语言相比,函数的 this 关键字在 JavaScript 中的表现略有不同,此外,在严格模式和非严格模式之间也会有一些差别。	<br>
	在绝大多数情况下,函数的调用方式决定了 this 的值(运行时绑定)。this 不能在执行期间被赋值,并且在每次函数被调用时 this 的值也可能会不同。ES5 引入了 bind 方法来设置函数的 this 值,而不用考虑函数如何被调用的。ES2015 引入了箭头函数,箭头函数不提供自身的 this 绑定(this 的值将保持为闭合词法上下文的值)。<br>

18.js 的typeof返回有哪些数据类型?

答案解析:
	string,number,Boolean,undefined,object,function, symbol(es6)

19.什么是闭包?有什么特点?

答案解析:
	闭包(closure)是一个函数以及其捆绑的周边环境状态(lexical environment,词法环境)的引用的组合。换而言之,闭包让开发者可以从内部函数访问外部函数的作用域。在 JavaScript 中,闭包会随着函数的创建而被同时创建。<br>
	-1.优点<br>
    	(1)可以从内部函数访问外部函数的作用域中的变量,且访问到的变量长期驻扎在内存中,可供之后使用<br>
    	(2)避免变量污染全局<br>
    	(3)把变量存到独立的作用域,作为私有成员存在<br>
	-2.缺点<br>
		(1)对内存消耗有负面影响。因内部函数保存了对外部变量的引用,导致无法被垃圾回收,增大内存使用量,所以使用不当会导致内存泄漏<br>
		(2)对处理速度具有负面影响。闭包的层级决定了引用的外部变量在查找时经过的作用域链长度<br>

20.简述js继承的方式?

答案解析:
	(1)所谓继承就是通过某种方式让一个对象可以访问到另一个对象中的属性和方法。<br>
	(2)在JavaScript中常用的几种继承方式<br>
		-1.原型链继承:通过实例化一个函数使子类的原型指向父类的实例,子类就可以调用到父类的属性和方法。<br>
		-2.借用构造函数继承:在子类型的构造函数中调用超类型的构造函数。<br>
		-3.组合模式继承:组合式继承是将原型链继承和构造函数继承二者取其长处组合到一起而产生的继承模式。<br>
		-4.ES6中class的继承(新)<br>

21.深拷贝和浅拷贝的区别?

答案解析:
	浅拷贝(shallowCopy)只是增加了一个指针指向已存在的内存地址,<br>
	深拷贝(deepCopy)是增加了一个指针并且申请了一个新的内存,使这个增加的指针指向这个新的内存.<br>

22.如何实现深拷贝?

答案解析:
	(1)常用:使用JSON.parse(JSON.stringify(obj))<br>
		原理是把一个对象序列化成为一个JSON字符串,将对象的内容转换成字符串的形式再保存在磁盘上,再用JSON.parse()反序列化将JSON字符串变成一个新的对象<br>
		缺点是: 会忽略undefined、symbol、funciton<br>
    (2)实现:递归+判断类型<br>
      一个简单的代码:<br>
      <script>
      // 数字 字符串 function是不需要拷贝的<br>
      function deepClone(value) {  <br><br>
          if (value == null) return value;  <br>
          if (typeof value !== 'object') return value;<br>
          if (value instanceof RegExp) return new RegExp(value); <br> 
          if (value instanceof Date) return new Date(value);  <br>
          // 我要判断 value 是对象还是数组 如果是对象 就产生对象 是数组就产生数组 <br> 
          let obj = new value.constructor;  <br>
          for(let key in value){    <br>
              obj[key] = deepClone(value[key]); // 看一看当前的值是不是一个对象  <br>
          }  <br>
          return obj;<br>
      }<br>
      </script>

23.javascript 的垃圾回收机制讲一下?

答案解析:
	JavaScript 在创建对象(对象、字符串等)时会为它们分配内存,不再使用对时会“自动”释放内存,这个过程称为垃圾收集。 释放内存 — 释放所有不再使用的内存,使之成为自由内存,并可以被重利用。<br>
	四种常见的内存泄漏:全局变量,未清除的定时器,闭包,以及 dom 的引用<br>

24.介绍下 promise 以及优缺点?

答案解析:
	(1)Promise 对象用于表示一个异步操作的最终完成(或失败)及其结果值。<br>
    (2)一个 Promise 必然处于以下几种状态之一:<br>
    	待定(pending):初始状态,既没有被兑现,也没有被拒绝。<br>
    	已兑现(fulfilled):意味着操作成功完成。<br>
    	已拒绝(rejected):意味着操作失败。<br>
    (3)Promise对象接受一个回调函数作为参数, 该回调函数接受两个参数,分别是成功时的回调resolve和失败时的回调reject;<br>
      	在.then中获取resolve的值,在.catch中获取reject的值;<br>
	 Promise优点<br>
		①统一异步 API<br>
		Promise 的一个重要优点是它将逐渐被用作浏览器的异步 API ,统一现在各种各样的 API ,以及不兼容的模式和手法。<br>
		②Promise 与事件对比<br>
		和事件相比较, Promise 更适合处理一次性的结果。在结果计算出来之前或之后注册回调函数都是可以的,都可以拿到正确的值。 Promise 的这个优点很自然。但是,不能使用 Promise 处理多次触发的事件。链式处理是 Promise 的又一优点,但是事件却不能这样链式处理。<br>
		③Promise 与回调对比<br>
		解决了回调地狱的问题,将异步操作以同步操作的流程表达出来。<br>
		④Promise 带来的额外好处是包含了更好的错误处理方式(包含了异常处理),并且写起来很轻松(因为可以重用一些同步的工具,比如 Array.prototype.map() )。<br>
	Promise缺点<br>
		①无法取消Promise,一旦新建它就会立即执行,无法中途取消。<br>
		②如果不设置回调函数,Promise内部抛出的错误,不会反应到外部。<br>
		③当处于Pending状态时,无法得知目前进展到哪一个阶段(刚刚开始还是即将完成)。<br>
		④Promise 真正执行回调的时候,定义 Promise 那部分实际上已经走完了,所以 Promise 的报错堆栈上下文不太友好<br>

25.请介绍一下XMLhttprequest对象?

答案解析:
	Ajax的核心是JavaScript对象XmlHttpRequest。该对象在Internet Explorer 5中首次引入,它是一种支持异步请求的技术。简而言之,XmlHttpRequest使您可以使用JavaScript向服务器提出请求并处理响应,而不阻塞用户。通过XMLHttpRequest对象,Web开发人员可以在页面加载以后进行页面的局部更新。

26.请描述一下 cookies,sessionStorage 和 localStorage 的区别?

答案解析:
	(1)cookie是浏览器自动携带在请求里发送给服务端去验证的<br>
	(2)sessionStorage和localStorage不会自动携带<br>
	(3)cookie体积相对sessionStorage localStorage小<br>
	(4)后端可以设置cookie之后,前端修改不了的;<br>
	(5)cookie可以设置过期时间<br>
	(6)cookie是用来做状态保持的,因为http请求时无状态的<br>
	(7)cookie是用户第一次访问服务器服务器颁发给浏览器的,第二次请求就会携带<br>
	(8)sessionStorage 存储在内存中 关闭浏览器数据会消失<br>
	(9)localStorage 关闭浏览器数据不会消失 需要手动去清除<br>

27.浏览器缓存策略?

答案解析:
	浏览器每次发起请求时,先在本地缓存中查找结果以及缓存标识,根据缓存标识来判断是否使用本地缓存。如果缓存有效,则使 用本地缓存;否则,则向服务器发起请求并携带缓存标识。根据是否需向服务器发起HTTP请求,将缓存过程划分为两个部分: 强制缓存和协商缓存,强缓优先于协商缓存。

28.简述同源策略与跨域?

答案解析:
	同源策略是一种约定,它是浏览器最核心的也最基本的安全功能,如果缺少了同源策略,则浏览器的正常功能可能会受到影响。<br><br>
	当协议,主机,和端口号有一个不同时,就是跨域<br>

29.跨域解决方案?

答案解析:
	1.(后端)服务器配置CORS(跨域资源共享)<br>
	2.(后端)node.js或nginx,反向代理,把跨域改造成同域<br>
	3.(前端)将JSON升级成JSONP,在JSON的基础上,利用script 标签可以跨域的特性,加上头设置<br>

30.从浏览器地址栏输入URL到显示页面的步骤

答案解析:
	1. 浏览器根据请求的URL交给DNS域名解析,找到真实IP,向服务器发起请求;<br>
	2. 服务器交给后台处理完成后返回数据,浏览器接收文件(html,js,css,图像等);<br>
	3. 浏览器对加载到的资源(html,js,css等)进行语法解析,建立相应的内部数据结构(如HTML的DOM);<br>
	4. 载入解析到的资源文件,渲染页面,完成<br>

31.阐述一下浏览器的事件循环?

答案解析:
	JavaScript的任务分为两种同步和异步,它们的处理方式也各自不同,同步任务是直接放在主线程上排队依次执行,异步任务会放在任务队列中,若有多个异步任务则需要在任务队列中排队等待,任务队列类似于缓冲区,任务下一步会被移到调用栈然后主线程执行调用栈的任务。<br>
    浏览器端事件循环中的异步队列有两种:macro(宏任务)队列和 micro(微任务)队列。<br>
    当某个宏任务执行完后,会查看是否有微任务队列。如果有,先执行微任务队列中的所有任务,如果没有,会读取宏任务队列中排在最前的任务,执行宏任务的过程中,遇到微任务,依次加入微任务队列。栈空后,再次读取微任务队列里的任务,依次类推。<br>

32.事件冒泡以及如何阻止事件冒泡?

答案解析:
	当一个事件发生在具有父元素的元素上时,现代浏览器运行两个不同的阶段 - 捕获阶段和冒泡阶段。<br><br>
	在现代浏览器中,默认情况下,所有事件处理程序都在冒泡阶段进行注册。触发子元素一个事件,然后这个事件顺着嵌套顺序在父元素上触发。<br>
	防止事件冒泡的一种方法是使用 event.cancelBubble 或 event.stopPropagation()(低于 IE 9)<br>

33.什么是防抖和节流?

答案解析:
	防抖:简单地说,就是 当一个动作连续触发,只执行最后一次。<br>
   	 	一般使用场景:<br>
		-1.登录、发短信等按钮避免用户点击太快,以致于发送了多次请求,需要防抖<br>
		-2.调整浏览器窗口大小时,resize 次数过于频繁,造成计算过多,此时需要一次到位,就用到了防抖<br>
         -3.搜索框搜索内容,实现实时搜索的时候<br>
    节流:简单地说,就是限制一个动作在一段时间内只能执行一次<br>
    	一般使用场景:<br>
		-1.scroll 事件,每隔一秒计算一次位置信息等<br>

34.如何实现防抖和节流?

答案解析:
    <script>
  		//防抖
		const debounce = (fun, delay = 500) => {
            let timer = null //设定一个定时器
            return function (...args) {
                clearTimeout(timer);
                timer = setTimeout(() => {
                    fun.apply(this, args)
                }, delay)
            }
        }
        //节流
        
        const throttle = (fun, delay = 1000) => {
          let flag = true;
          return function (...args) {
              if (!flag) return;
              flag = false
              setTimeout(() => {
                  fun.apply(this, args)
                  flag = true
              }, delay)
          }
      }
    </script>

35.JSONP 的原理是什么?

答案解析:
	尽管浏览器有同源策略,但是 script 标签的 src 属性不会被同源策略所约束,可以获取任意服务器上的脚本并执行。jsonp 通过插入 script 标签的方式来实现跨域,参数只能通过 url 传入,仅能支持 get 请求<br>。	
    Step1: 创建 callback 方法<br>
    Step2: 插入 script 标签<br>
    Step3: 后台接受到请求,解析前端传过去的 callback 方法,返回该方法的调用,并且数据作为参数传入该方法<br>
    Step4: 前端执行服务端返回的方法调用<br>

36.异步加载JS的方式有哪些?

答案解析:
  异步加载js的方式有两种:defer和async。<br>
  二者共同点:<br>
    1、defer和async都是去异步加载外部的js脚本文件的。<br>
    2、defer和async都不会阻塞页面的解析。<br>
  区别点:<br>
    1、执行顺序方面<br>
      多个带async属性的标签,不能保证加载的顺序;<br>
      多个带defer属性的标签,按照加载顺序执行。<br>
    2、脚本是否并行执行方面<br>
      async属性,表示后续文档的加载和执行,与js脚本的加载和执行是并行进行的,即异步执行。<br>
      defer属性,加载后续文档的过程和js脚本的加载(此时仅加载不执行)是并行进行的(异步),js脚本需要等到文档所有元素解析完成之后才执行。<br>

37.哪些操作会造成内存泄漏?

答案解析:
	内存泄漏指任何对象在您不再拥有或需要它之后仍然存在<br>
	setTimeout 的第一个参数使用字符串而非函数的话,会引发内存泄漏<br>
	闭包、控制台日志、循环(在两个对象彼此引用且彼此保留时,就会产生一个循环)<br>

38.事件传播的三个阶段是什么?

答案解析:
	捕获\目标\冒泡

39.同步和异步的区别?

答案解析:
	同步和异步的区别是同步是阻塞模式,异步是非阻塞模式。同步就是指一个进程在执行某个请求的时候,若该请求需要一段时间才能返回信息,那么这个进程将会一直等待下去,直到收到返回信息才继续执行下去。<br>
	异步是指进程不需要一直等下去,而是继续执行下面的操作,不管其他进程的状态。当有消息返回时系统会通知进程进行处理,这样可以提高执行的效率。<br>

40.前端如何压缩图片?

答案解析:
	首先介绍下压缩的大概流程<br>
        -1.通过原生的input标签拿到要上传的图片文件<br>
        -2.将图片文件转化成img元素标签<br>
        -3.在canvas上压缩绘制该HTMLImageElement<br>
    核心步骤:<br>
    	-1.拿到转化后的img元素后,先取出该元素的宽高度,这个宽高度就是实际图片文件的宽高度。<br>
    	-2.然后定义一个最大限度的宽高度,如果超过这个限制宽高度,则进行等比例的缩放。<br>
    	-3.计算好将要压缩的尺寸后,创建canvas实例,设置canvas的宽高度为压缩计算后的尺寸,并将img绘制到上面<br>

41.new操作符到底干了什么?

答案解析:
	function Person(name){ <br>
      //--------------------伪代码----------------------- <br>
      var obj = new Object(); //创建了空对象 <br>
      this = obj //obj赋值给this <br>
      this.proto = Person.prototype //实例对象的原型就是构造函数的原型 <br>
      this.name = name;//定义实例属性和方法 <br>
      return this; //返回this <br>
	}<br>
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值