初级程序员必备的十大技能之编程语言(二)

简介: 教程来源 https://www.ltglu.cn/ 函数是代码的“乐高积木”,可封装复用逻辑。本文详解函数定义与调用、值/引用传递差异、作用域(LEGB规则)、默认参数、*args/**kwargs、箭头函数特性及递归原理,覆盖JS/Python/Java三语言实践。

三、函数:代码的“乐高积木”

3.1 函数基础
函数是将一段代码封装起来,给它一个名字,然后在需要时调用它。

函数定义与调用

// JavaScript 函数定义
function greet(name) {
    // 参数 name
    let message = "你好," + name + "!";
    return message;  // 返回值
}

// 调用函数
let result = greet("张三");
console.log(result);  // "你好,张三!"
# Python 函数定义
def greet(name):
    """这是一个简单的问候函数"""  # 文档字符串
    message = f"你好,{name}!"
    return message

# 调用
result = greet("张三")
print(result)
// Java 函数定义(方法)
public static String greet(String name) {
    String message = "你好," + name + "!";
    return message;
}

// 调用
String result = greet("张三");
System.out.println(result);

3.2 参数传递的奥秘
值传递 vs 引用传递

// 基本类型(值传递)—— 传递的是值的副本
function modifyNumber(x) {
    x = x + 10;
    console.log("函数内部:", x);  // 15
}

let a = 5;
modifyNumber(a);
console.log("函数外部:", a);  // 5(未被修改!)

// 对象类型(引用传递)—— 传递的是引用
function modifyObject(obj) {
    obj.age = 30;  // 修改对象的属性
    console.log("函数内部:", obj.age);  // 30
}

let person = { name: "张三", age: 25 };
modifyObject(person);
console.log("函数外部:", person.age);  // 30(被修改了!)

重要理解:

数字、字符串、布尔值→传递的是副本,原变量不变

数组、对象→传递的是引用,函数内部修改会影响外部

3.3 函数作用域
作用域决定了变量在哪里可以被访问。

// 全局作用域
let globalVar = "我在任何地方都能被访问";

function testScope() {
    // 函数作用域
    let localVar = "我只能在函数内部被访问";
    console.log(globalVar);  // ✅ 可以访问
    console.log(localVar);   // ✅ 可以访问
}

console.log(globalVar);  // ✅ 可以访问
// console.log(localVar); // ❌ 报错:localVar 未定义
# Python 的作用域(LEGB 规则)
x = "全局变量"

def outer():
    y = "外部函数变量"

    def inner():
        z = "内部函数变量"
        print(x)  # 查找:内部 → 外部 → 全局
        print(y)
        print(z)

    inner()
    # print(z)  # ❌ 无法访问内部函数变量

outer()

LEGB 查找顺序:

Local:当前函数内部

Enclosing:外层函数

Global:模块全局

Built-in:Python 内置

3.4 高级函数特性
默认参数值

# Python
def greet(name, greeting="你好"):
    return f"{greeting},{name}!"

print(greet("张三"))          # "你好,张三!"
print(greet("张三", "嗨"))    # "嗨,张三!"
// JavaScript
function greet(name, greeting = "你好") {
    return `${greeting},${name}!`;
}

⚠️ 陷阱:不要使用可变对象作为默认参数

# ❌ 错误示例
def add_item(item, list=[]):  # 默认列表会在函数定义时创建
    list.append(item)
    return list

print(add_item("a"))  # ["a"]
print(add_item("b"))  # ["a", "b"] ❌ 意外地累积了

# ✅ 正确做法
def add_item(item, list=None):
    if list is None:
        list = []
    list.append(item)
    return list

print(add_item("a"))  # ["a"]
print(add_item("b"))  # ["b"]

可变参数(args 和 *kwargs)

# *args:接收任意多个位置参数(打包为元组)
def sum_all(*numbers):
    total = 0
    for num in numbers:
        total += num
    return total

print(sum_all(1, 2, 3, 4, 5))  # 15

# **kwargs:接收任意多个关键字参数(打包为字典)
def print_info(**info):
    for key, value in info.items():
        print(f"{key}: {value}")

print_info(name="张三", age=25, city="北京")
// JavaScript 的剩余参数(类似 *args)
function sumAll(...numbers) {
    return numbers.reduce((total, num) => total + num, 0);
}

// 收集剩余参数
function introduce(name, ...hobbies) {
    console.log(`${name} 喜欢:${hobbies.join("、")}`);
}

箭头函数(JavaScript)

// 传统函数
function add(a, b) {
    return a + b;
}

// 箭头函数(简洁写法)
const add = (a, b) => a + b;

// 只有一个参数可省略括号
const double = x => x * 2;

// 无参数需要空括号
const greet = () => "你好";

// 返回对象需要括号包裹
const createUser = name => ({ name: name, createdAt: new Date() });

箭头函数 vs 普通函数:

箭头函数没有自己的 this(继承外层)

不能用作构造函数(不能 new)

没有 arguments 对象

递归函数
函数调用自身,适用于树形结构、分治算法等场景。

# 经典案例:计算阶乘 n! = n * (n-1) * ... * 1
def factorial(n):
    # 基线条件:必须有一个终止条件
    if n <= 1:
        return 1
    # 递归条件:函数调用自身
    return n * factorial(n - 1)

print(factorial(5))  # 120

# 执行过程:
# factorial(5) = 5 * factorial(4)
#             = 5 * (4 * factorial(3))
#             = 5 * (4 * (3 * factorial(2)))
#             = 5 * (4 * (3 * (2 * factorial(1))))
#             = 5 * (4 * (3 * (2 * 1)))
#             = 120

递归 vs 循环:
image.png
来源:
https://ltglu.cn/

相关文章
|
13天前
|
人工智能 JSON 供应链
畅用7个月无影 JVS Claw |手把手教你把JVS改造成「科研与产业地理情报可视化大师」
LucianaiB分享零成本畅用JVS Claw教程(学生认证享7个月使用权),并开源GeoMind项目——将JVS改造为科研与产业地理情报可视化AI助手,支持飞书文档解析、地理编码与腾讯地图可视化,助力产业关系图谱构建。
23480 11
畅用7个月无影 JVS Claw |手把手教你把JVS改造成「科研与产业地理情报可视化大师」
|
17天前
|
人工智能 缓存 BI
Claude Code + DeepSeek V4-Pro 真实评测:除了贵,没别的毛病
JeecgBoot AI专题研究 把 Claude Code 接入 DeepSeek V4Pro,跑完 Skills —— OA 审批、大屏、报表、部署 5 大实战场景后的真实体验 ![](https://oscimg.oschina.net/oscnet/up608d34aeb6bafc47f
5397 20
Claude Code + DeepSeek V4-Pro 真实评测:除了贵,没别的毛病
|
18天前
|
人工智能 JSON BI
DeepSeek V4 来了!超越 Claude Sonnet 4.5,赶紧对接 Claude Code 体验一把
JeecgBoot AI专题研究 把 Claude Code 接入 DeepSeek V4Pro 的真实体验与避坑记录 本文记录我将 Claude Code 对接 DeepSeek 最新模型(V4Pro)后的真实体验,测试了 Skills 自动化查询和积木报表 AI 建表两个场景——有惊喜,也踩
6437 16
|
6天前
|
人工智能 缓存 Shell
Claude Code 全攻略:命令大全 + 实战工作流(完整版)
Claude Code 是一款运行在终端环境下的 AI 编码助手,能够直接在项目目录中理解代码结构、编辑文件、执行命令、执行开发计划,并支持持久化记忆、上下文压缩、后台任务、多模型切换等专业能力。对于日常开发、项目维护、快速重构、代码审查等场景,它可以大幅减少手动操作、提升编码效率。本文从常用命令、界面模式、核心指令、记忆机制、图片处理、进阶工作流等维度完整说明,帮助开发者快速上手并稳定使用。
1552 3
|
6天前
|
前端开发 API 内存技术
对比claude code等编程cli工具与deepseek v4的适配情况
DeepSeek V4发布后,多家编程工具因未适配其强制要求的`reasoning_content`字段而报错。本文对比Claude Code、GitHub Copilot、Langcli、OpenCode及DeepSeek-TUI等主流工具的兼容性:Claude Code需按官方方式配置;Langcli表现最佳,开箱即用且无报错;Copilot与OpenCode暂未修复问题;DeepSeek-TUI尚处早期阶段。
1052 2
对比claude code等编程cli工具与deepseek v4的适配情况
|
2天前
|
人工智能 BI 持续交付
Claude Code 深度适配 DeepSeek V4-Pro 实测:全场景通关与真实体验报告
在 AI 编程工具日趋主流的今天,Claude Code 凭借强大的任务执行、工具调用与工程化能力,成为开发者与自动化运维的核心效率工具。但随着原生模型账号稳定性问题频发,寻找一套兼容、稳定、能力在线的替代方案变得尤为重要。DeepSeek V4-Pro 作为新一代高性能大模型,提供了完整兼容 Claude 协议的 API 接口,只需简单配置即可无缝驱动 Claude Code,且在任务执行、工具调用、复杂流程处理上表现极为稳定。
696 0
|
1月前
|
人工智能 自然语言处理 安全
Claude Code 全攻略:命令大全 + 实战工作流(建议收藏)
本文介绍了Claude Code终端AI助手的使用指南,主要内容包括:1)常用命令如版本查看、项目启动和更新;2)三种工作模式切换及界面说明;3)核心功能指令速查表,包含初始化、压缩对话、清除历史等操作;4)详细解析了/init、/help、/clear、/compact、/memory等关键命令的使用场景和语法。文章通过丰富的界面截图和场景示例,帮助开发者快速掌握如何通过命令行和交互界面高效使用Claude Code进行项目开发,特别强调了CLAUDE.md文件作为项目知识库的核心作用。
26920 65
Claude Code 全攻略:命令大全 + 实战工作流(建议收藏)

热门文章

最新文章