目录

1.变量的声明与定义有什么区别?

2.sizeof与strlen的区别?

3.c语言关键字static与c++的关键字static有什么区别?

4.c中的malloc与c++中的new有什么区别?

5.简述c,c++程序编译的内存分配请情况?


1.变量的声明与定义有什么区别?

为变量分配地址空间的称为定义,不分配地址空间的称为声明。一个变量可以再多个地方声明,但只能在一个地方定义。加入extern修饰的是变量的声明,说明此变量将在文件以外或者文件以后部分定义。说明很多时候一个变量只声明不分配内存空间,直到使用时才初始化,分配内存空间,如外部变量。

2.sizeof与strlen的区别?

在 C 语言中,sizeofstrlen是两个常用但功能完全不同的工具,主要区别如下:

本质与用途

sizeof:是一个运算符,用于计算变量、数据类型或表达式所占用的内存字节数

strlen:是标准库函数(需要#include <string.h>),用于计算字符串中字符的个数(不包括结束符'\0'

处理对象

sizeof:可以用于任何数据类型(int、float、数组、结构体等)和变量

strlen:只能用于以'\0'结尾的字符串(字符数组)

计算结果

sizeof:计算的是整个对象所占用的内存大小,对于字符串数组会包含结束符'\0'

strlen:计算的是从起始地址到第一个'\0'之间的字符数,不包含'\0'

其他差异

sizeof在编译时计算结果,而strlen在运行时计算

sizeof的结果是size_t类型,strlen的返回值也是size_t类型

对未初始化的字符数组使用strlen可能导致不可预测的结果(因为可能找不到'\0'

数组作为sizeof的参数不退化 作为strlen的参数 退化为指针

简单来说,sizeof关注 "内存大小",strlen关注 "字符串长度",这是它们最核心的区别。

3.c语言关键字static与c++的关键字static有什么区别?

1. 相同点(两种语言共有的特性)

  • 修饰全局变量:将全局变量的作用域限制在当前文件(内部链接)
  • 修饰局部变量:延长局部变量的生命周期至程序结束,保留上次的值
  • 修饰函数:将函数的作用域限制在当前文件(内部链接)

2.不同点

  • c++的static还可以用来定义成员变量与函数,及静态成员与静态成员函数。

3. 核心区别总结

特性 C 语言中的static C++ 中的static
基本功能 控制作用域和生命周期 包含 C 的所有功能
类相关 不支持(无类概念) 支持静态成员变量、静态成员函数
面向对象 无相关特性 用于实现类级别的共享数据和方法

简单说,C++ 中的static继承了 C 语言的所有功能,并在面向对象编程中扩展了新的用途,主要用于实现类级别的共享数据和方法。

4.c中的malloc与c++中的new有什么区别?

C 语言中的malloc和 C++ 中的new都是用于动态内存分配的工具,但它们在功能、用法和特性上有显著区别,主要差异如下:

1. 本质与所属范畴

  • malloc:是 C 语言标准库函数(需#include <stdlib.h>),在 C++ 中也可使用

  • new:是 C++ 的关键字,是 C++ 语言本身的一部分,不是函数

2. 功能范围

  • malloc:仅负责分配指定大小的内存块,返回void*类型指针

  • new:不仅分配内存,还会自动调用对象的构造函数初始化对象

// C语言风格(malloc)
int* p1 = (int*)malloc(sizeof(int));  // 仅分配内存,未初始化
if (p1 == NULL) { /* 处理内存分配失败 */ }

// C++风格(new)
int* p2 = new int;  // 分配内存并初始化(基本类型默认初始化)
int* p3 = new int(10);  // 分配内存并初始化为10

// 对于类对象
class MyClass {
public:
    MyClass() { /* 构造函数 */ }
};

MyClass* obj1 = (MyClass*)malloc(sizeof(MyClass));  // 仅分配内存,未调用构造函数
MyClass* obj2 = new MyClass;  // 分配内存并调用构造函数

3. 内存分配失败处理

  • malloc:分配失败时返回NULL指针,需要手动检查

  • new:分配失败时默认抛出std::bad_alloc异常(可指定不抛出异常,返回NULL

4. 数组内存分配

  • malloc:分配数组时需手动计算总字节数,返回的指针需显式转换
  • new:支持数组形式,会自动计算大小,并对数组元素调用构造函数
// 分配数组
int* arr1 = (int*)malloc(5 * sizeof(int));  // C风格
int* arr2 = new int[5];  // C++风格,会默认初始化
int* arr3 = new int[5] {1, 2, 3, 4, 5};  // C++11后支持初始化列表

// 对应释放
free(arr1);
delete[] arr2;  // 注意数组要用delete[]
delete[] arr3;

5. 对应释放方式

  • malloc 分配的内存:必须用free()释放,且free()不调用析构函数
  • new 分配的内存:必须用delete释放(数组用delete[]),会自动调用析构函数

6. 重载能力

  • malloc:作为库函数,无法重载
  • new:可以重载,允许自定义内存分配策略(通过重载operator new

总结对比表

特性 malloc new
性质 库函数 关键字
功能 仅分配内存 分配内存 + 调用构造函数
返回类型 void*(需显式转换) 具体类型指针(无需转换)
失败处理 返回 NULL 默认抛出异常
数组分配 需手动计算大小 支持new[]语法
释放方式 free() delete/delete[]
析构函数 不调用 自动调用
重载 不能 可以

5.简述c,c++程序编译的内存分配请情况?

c,c++内存分配方式可以分为以下三种:

(1).从静态存储区域分配:

特点:程序启动时分配,生命周期贯穿整个程序

内容:全局变量(定义在函数外的变量)

    static修饰的静态变量(包括全局静态和局部静态)

分类:已初始化区:存储初始化的全局 / 静态变量

          未初始化区(BSS 段):存储未初始化的全局 / 静态变量(默认初始化为 0)

(2).在栈上分配:

特点:自动分配与释放,遵循 "先进后出" 原则

内容:函数的局部变量(包括形参)

           函数调用时的返回地址

           临时变量和上下文信息

大小:通常固定(可配置),较小(几 MB)

(3).从堆上分配:

特点:动态分配,需手动管理(C 用malloc/free,C++ 用new/delete

内容:程序运行中动态申请的内存

           如动态数组、对象等

大小:较大(可达 GB 级别),受限于系统内存

(4).常量存储区:

特点:存储只读数据,不可修改

内容:字符串常量(如"hello world"

    const修饰的常量(C++ 中可能优化到栈或全局区)

(5).程序代码区:

特点:存储可执行代码,只读(防止意外修改)

内容:程序的机器指令

           函数体的二进制代码

一个c,c++程序编译时内存分为5大存储区域:堆区,栈区,全局区,程序代码区,文字常量区

更多推荐