Web-Dev-For-Beginners 实战作业:用 JavaScript 函数构建可复用逻辑(Functions & Methods 编程练习指南)
【免费下载链接】Web-Dev-For-Beginners24 Lessons, 12 Weeks, Get Started as a Web Developer项目地址: https://gitcode.com/GitHub_Trending/we/Web-Dev-For-Beginners
本文是 Web-Dev-For-Beginners 课程中《JavaScript Basics: Methods and Functions》配套作业 "Fun with Functions" 的完整实战指南。你将通过 6 个由浅入深的编程任务,亲手实践函数声明、参数与默认值、
return返回值三大核心概念,并对照仓库内真实项目源码(如银行项目、太空游戏、打字游戏)理解这些能力在真实 Web 应用中的落地方式。学完本文,你将能独立写出结构清晰、可复用、可测试的 JavaScript 函数。
作业背景:从课程到实践
本作业对应课程 2-js-basics/2-functions-methods/README.md 的最终环节。课程中你已经掌握:
- 函数声明语法
function nameOfFunction() { ... }与调用方式nameOfFunction(); - 参数(parameters)作为占位符接收传入值,多个参数用逗号分隔;
- 默认参数(default values)通过等号
=为可选参数提供后备值; return语句将计算结果交还给调用方,且遇到return时函数立即结束;- 现代语法:匿名函数、箭头函数(
=>)、以及函数作为参数传入(回调函数)。
而这份作业要求你把上述知识点综合运用到 6 个具体函数上,从"无参数、只打印"到"必选参数 + 默认值 + 返回值"层层递进,最终完成一次完整的"定义—实现—测试"开发闭环。下面的完整任务拆解严格依据作业原文 translations/en/2-js-basics/2-functions-methods/assignment.md 展开。
任务清单总览
作业要求新建一个名为functions-practice.js的 JavaScript 文件,依次实现 6 个函数,并在文件末尾用console.log()调用它们以验证结果。整体任务分五部分:
| 部分 | 函数 | 参数 | 返回值 | 核心练习点 |
|---|---|---|---|---|
| Part 1 | sayHello | 无 | 无(仅输出) | 最简单的函数声明与调用 |
| Part 1 | introduceYourself | name(必选) | 无(仅输出) | 参数传递、模板字符串 |
| Part 2 | greetPerson | name(必选)、greeting(默认"Hello") | 无(仅输出) | 默认参数 |
| Part 3 | addNumbers | num1、num2 | 两数之和 | return返回值 |
| Part 3 | createFullName | firstName、lastName | 拼接后的完整名字 | 返回值 + 字符串拼接 |
| Part 4 | calculateTip | billAmount(必选)、tipPercentage(默认 15) | 小费金额 | 默认值 + 计算 + 返回 |
设计意图很清晰:前 3 个函数练习"输出型"函数(执行动作),后 3 个练习"计算型"函数(返回数据),这也呼应了课程 README 中的关键观点——返回值让调用方决定如何使用结果,使代码更加模块化、可复用。
Part 1:从零开始的基本函数
1.1 无参数函数sayHello
这是函数的最简形态——不需要任何输入,只执行一段固定的代码:
function sayHello() { console.log("Hello!"); }对照课程中的经典示例 2-js-basics/2-functions-methods/README.md:
function displayGreeting() { console.log('Hello, world!'); } // 调用 displayGreeting();两者的结构完全一致:function关键字声明、函数名、空括号()(表示不需要参数)、花括号{}包裹函数体。调用时必须带括号sayHello()——省略括号不会执行函数,只是引用函数本身(这在后面"函数作为参数"的场景中反而是关键技巧)。
1.2 带参数函数introduceYourself
参数让同一个函数能对不同输入做出不同反应:
function introduceYourself(name) { console.log(`Hi, my name is ${name}`); }这里使用了模板字符串(template literal)——用反引号`包裹字符串,用${}插入变量。课程 README 中的displayGreeting(name)是同一模式的经典演示:
function displayGreeting(name) { const message = `Hello, ${name}!`; console.log(message); } displayGreeting('Christopher'); // 显示 "Hello, Christopher!"调用introduceYourself("Sarah")时,字符串"Sarah"会被赋值给参数name,函数体中的${name}就会被替换为实际值,输出Hi, my name is Sarah。
Part 2:默认参数让函数更灵活
第三个函数引入作业的重点考察点——默认参数:
function greetPerson(name, greeting = "Hello") { console.log(`${greeting}, ${name}!`); }这里的规则是:name是必选参数,greeting是可选参数——当调用方未提供第二个实参时,JavaScript 自动使用默认值"Hello"。这正是课程 README 中displayGreeting(name, salutation='Hello')的用法:
function displayGreeting(name, salutation='Hello') { console.log(`${salutation}, ${name}`); } displayGreeting('Christopher'); // 显示 "Hello, Christopher"(使用默认值) displayGreeting('Christopher', 'Hi'); // 显示 "Hi, Christopher"(传入自定义值)使用要点:
- 默认值通过等号
=在参数列表中直接指定,语法与变量赋值一致; - 默认参数使函数"开箱即用"(用户不传也能工作),同时保留定制能力;
- 带默认值的参数一般放在参数列表靠后的位置,避免调用时位置错乱。
Part 3:用 return 返回计算结果
前两个函数只往控制台打印信息,而计算型函数需要把结果"交还"给调用方,这就需要return语句。课程 README 明确指出:函数执行到return时立即停止,并把该值返回给调用者。
3.1 求和函数addNumbers
function addNumbers(num1, num2) { return num1 + num2; }调用时,返回值可以存入变量,也可以直接用于表达式:
const sum = addNumbers(5, 3); console.log(`The sum is: ${sum}`); // The sum is: 8对照课程中的createGreetingMessage示例:
function createGreetingMessage(name) { const message = `Hello, ${name}`; return message; } const greetingMessage = createGreetingMessage('Christopher'); // greetingMessage 现在包含 "Hello, Christopher"3.2 拼接函数createFullName
function createFullName(firstName, lastName) { return firstName + " " + lastName; }返回的字符串同样可以被存储、打印或传给其他函数:
const fullName = createFullName("John", "Doe"); console.log(`Full name: ${fullName}`); // Full name: John Doe返回值 vs 直接打印的核心区别:返回值的函数把"决定权"交给调用方——你可以打印它、存进变量、拼进网页、或作为参数传给另一个函数;而只打印的函数则无法把结果用于后续计算。这也是评分标准中"该返回的函数正确返回、不该返回的函数只执行动作"的判定依据。
Part 4:综合实战——带默认值的计算函数
calculateTip是本次作业的"收官之作",它同时考察参数、默认值与返回值三个知识点:
function calculateTip(billAmount, tipPercentage = 15) { return (billAmount * tipPercentage) / 100; }逻辑拆解:小费金额 = 账单金额 × 小费百分比 ÷ 100。billAmount为必选;tipPercentage默认 15,代表 15% 的标准小费比例。当调用方只传账单金额时,默认按 15% 计算:
const tip = calculateTip(50); // 默认 15% → 7.5 console.log(`Tip for $50 bill: $${tip}`); // Tip for $50 bill: $7.5 // 也可以显式传入自定义小费比例 console.log(calculateTip(50, 20)); // 10一个常见的边界点:这里tipPercentage传的是"百分比数值"(15 表示 15%),因此需要在函数内部除以 100 换算。如果换一种约定——直接传入 0.15 表示比例——函数体就可以简化为billAmount * tipPercentage。两种约定都可行,关键是函数内部与调用方的约定要保持一致,这正是编写清晰函数时需要思考的"接口设计"问题。
Part 5:测试你的函数
作业要求在文件末尾通过实际调用验证每个函数。完整的测试代码段如下(来自作业原文 translations/en/2-js-basics/2-functions-methods/assignment.md):
// Test your functions here sayHello(); introduceYourself("Sarah"); greetPerson("Alex"); greetPerson("Maria", "Hi"); const sum = addNumbers(5, 3); console.log(`The sum is: ${sum}`); const fullName = createFullName("John", "Doe"); console.log(`Full name: ${fullName}`); const tip = calculateTip(50); console.log(`Tip for $50 bill: $${tip}`);注意观察其中的测试设计技巧:
greetPerson("Alex")与greetPerson("Maria", "Hi")成对出现,分别验证"默认值生效"与"自定义值生效"两条路径;- 对返回型函数,先用变量接收返回值,再打印——这验证了返回值确实可被外部使用;
calculateTip(50)刻意省略第二个参数,用于验证默认参数15是否生效。
运行方式:把functions-practice.js通过<script>标签引入 HTML,或在浏览器开发者工具(按F12打开)的 Console 面板中执行,即可看到全部输出。也可以使用 Node.js 直接运行:node functions-practice.js。
评分标准解读:如何拿到 Exemplary
作业提供了五维评分表,理解标准才能有的放矢:
| 评分维度 | 优秀(Exemplary)标准 |
|---|---|
| 函数创建 | 6 个函数全部正确实现,语法规范、命名符合约定 |
| 参数与默认值 | 必选参数、可选参数、默认值全部按要求使用正确 |
| 返回值 | 该返回的函数正确返回;不该返回的函数只执行动作(不画蛇添足) |
| 代码质量 | 代码整洁、组织良好,变量命名有意义,缩进规范 |
| 测试 | 所有函数都被适当调用,结果展示清晰 |
对照自查要点:
- 命名风格:使用 camelCase(如
calculateTip而非calculate_tip),与课程推荐的calculateTotal风格一致; - 专注单一职责:每个函数只做一件事——打印的就只打印,计算的就只返回;
- 测试覆盖两条路径:默认值路径与自定义值路径都要测到;
- 输出清晰:用带标签的模板字符串(如
Full name: ${fullName})让控制台结果一目了然。
挑战进阶:三个 Bonus 任务
作业为学有余力者准备了三个可选挑战,分别对应课程中的进阶概念 2-js-basics/2-functions-methods/README.md:
Bonus 1:改写为箭头函数
箭头函数省去function关键字,语法更简洁:
// 传统写法 function addNumbers(num1, num2) { return num1 + num2; } // 箭头函数写法 const addNumbers = (num1, num2) => num1 + num2;课程中的计时器示例展示了三种写法(传统具名函数、匿名函数、箭头函数)的等价性:
// 传统函数 function displayDone() { console.log('3 seconds has elapsed'); } setTimeout(displayDone, 3000); // 匿名函数 setTimeout(function() { console.log('3 seconds has elapsed'); }, 3000); // 箭头函数 setTimeout(() => { console.log('3 seconds has elapsed'); }, 3000);Bonus 2:函数作为参数(回调)
这个挑战要求"函数接受另一个函数作为参数"。核心技巧在于传递时省略括号——就像setTimeout(displayDone, 3000)中传入的是displayDone而非displayDone(),因为我们是把函数"交给"别人去调用,而不是自己调用。课程 README 指出,这是"当某事发生时执行某代码"(如定时器结束、用户点击按钮)这类场景的常用模式。
Bonus 3:输入校验
为函数添加健壮性检查,例如:
function calculateTip(billAmount, tipPercentage = 15) { if (typeof billAmount !== 'number' || billAmount < 0) { console.warn('Invalid bill amount:', billAmount); return 0; } return (billAmount * tipPercentage) / 100; }仓库源码佐证:这些模式在真实项目中如何被使用
本次作业练习的函数能力,在 Web-Dev-For-Beginners 仓库的真实项目源码中处处可见,可作为学习参照。
默认参数与查询工具函数——太空游戏
在 6-space-game/solution/app.js 的入口处,可以看到默认参数与箭头函数组合的典型用法:
const $ = (sel, ctx = document) => ctx.querySelector(sel);ctx参数带有默认值document——调用$('button')时从文档中查找,需要限定范围时再传入具体容器。这与作业中greeting = "Hello"、tipPercentage = 15的设计思路完全一致:提供合理默认值,让常见调用更简洁。
计算 + 返回的封装——银行项目
在 7-bank-project/solution/app.js 中,可以看到"接收参数、内部计算、返回结果"的完整封装模式:
function toCurrency(amount, currency) { ... } // 返回格式化后的金额字符串 function formatDate(dateStr) { ... } // 返回格式化后的日期 function isIsoCurrency(code) { ... } // 返回布尔校验结果这些正是addNumbers、createFullName这类返回型函数在真实业务中的放大版——把格式化、校验逻辑封装成可复用的纯函数,供页面各处调用。该文件中的异步封装则展示了回调与默认参数的综合运用:
async function getAccount(user) { return new Promise(resolve => { setTimeout(() => { ... resolve(...) }, 500); }); }箭头函数与回调——打字游戏
在 4-typing-game/solution/index.js 中,箭头函数大量用于事件回调与数据处理:
const getRandomQuote = () => quotes[Math.floor(Math.random() * quotes.length)]; startButton.addEventListener("click", startGame); typedValueElement.addEventListener("input", handleTyping);其中startGame、handleTyping作为具名函数被传入addEventListener,与 Bonus 2 "函数作为参数"的挑战一一对应;而renderQuote内部用map对数组逐项处理并拼接,正是"返回新数据供上层使用"思想的体现。
闭包与嵌套函数——植物培育器
在 3-terrarium/solution/script.js 中,dragElement内部定义了pointerDrag、elementDrag、stopElementDrag等嵌套函数(闭包),展示了函数内部组织子逻辑的实际场景,可作为"代码组织"维度的进阶参考。
小结:作业中的 6 个函数虽小,但sayHello→introduceYourself→greetPerson→addNumbers→createFullName→calculateTip这条练习路径,完整覆盖了函数从"打印输出"到"参数化"再到"返回数据"的能力演进。完成本作业后,你不仅具备了函数三大核心概念的实操能力,也为自己后续阅读、理解仓库中真实项目的模块化代码打下了基础。
【免费下载链接】Web-Dev-For-Beginners24 Lessons, 12 Weeks, Get Started as a Web Developer项目地址: https://gitcode.com/GitHub_Trending/we/Web-Dev-For-Beginners
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考