【C 语言】内存四区原理 ( 常量区示例 | 不同函数返回的相同字符串的指针地址相同 )

简介: 【C 语言】内存四区原理 ( 常量区示例 | 不同函数返回的相同字符串的指针地址相同 )

文章目录

前言

一、正常程序

二、获取相同的字符串内容

前言

C / C++ 编译器会对代码进行 词法分析 , 语法分析 , 句法分析 ;


然后对代码进行优化 ;


将 字符串常量 赋值给指针时 , 首先去 全局变量区 的 常量区 查询该 字符串常量是否存在 ,


如果存在 , 直接使用该 字符串常量地址 赋值给 char* 指针 ,

如果不存在 , 直接在常量区 创建一个新的字符串 , 然后将地址 赋值给 char* 指针 ;


下面的 2 22 个程序 , 分别演示 不同的字符串常量 和 相同的字符串常量 地址的区别 ;






一、正常程序


分别从两个函数中 , 获取两个不同的字符串 , 打印出这两个 字符串 内容 及 指针指向的地址 ;



代码示例 :


#include <stdio.h>
/*
 * 函数1 返回字符串 1
 */
char *get_str1()
{
    char *p1 = "abc";
    return p1;
}
/*
 * 函数2 返回字符串 2
 */
char *get_str2()
{
    char *p2 = "123";
    return p2;
}
int main()
{
    char *p1 = NULL;
    char *p2 = NULL;
    // 分别从 2 个函数中获取 2 个字符串
    p1 = get_str1();
    p2 = get_str2();
    // 打印 p1 , p2 指针指向的内存中的字符串数据
    // p1=abc, p2=123
    printf("p1=%s, p2=%s\n", p1, p2);
    // 打印 p1 , p2 指针指向的地址
    // p1=4210756, p2=4210760
    printf("p1=%d, p2=%d\n", p1, p2);
    return 0;
}



执行结果 : 打印出的字符串内容不同 , 字符串指针地址不同 ;


p1=abc, p2=123
p1=4210756, p2=4210760


image.png





二、获取相同的字符串内容


如果在 2 22 个函数中 , 获取的 字符串 是相同的字符串 ;


此时打印出两个函数的指针地址是相同的 , 这是因为 获取的 字符串 都是从 全局区 中的 常量区 中获取的 ;



代码示例 :


#include <stdio.h>
/*
 * 函数1 返回字符串 1
 */
char *get_str1()
{
    char *p1 = "abc";
    return p1;
}
/*
 * 函数2 返回字符串 2
 */
char *get_str2()
{
    char *p2 = "abc";
    return p2;
}
int main()
{
    char *p1 = NULL;
    char *p2 = NULL;
    // 分别从 2 个函数中获取 2 个字符串
    p1 = get_str1();
    p2 = get_str2();
    // 打印 p1 , p2 指针指向的内存中的字符串数据
    // p1=abc, p2=123
    printf("p1=%s, p2=%s\n", p1, p2);
    // 打印 p1 , p2 指针指向的地址
    // p1=4210756, p2=4210760
    printf("p1=%d, p2=%d\n", p1, p2);
    return 0;
}



执行结果 :


p1=abc, p2=abc
p1=4210756, p2=4210756


目录
相关文章
|
5天前
|
C语言
c语言指针总结
c语言指针总结
12 1
|
2天前
|
存储 程序员 编译器
C语言:动态内存管理
C语言:动态内存管理
9 1
|
2天前
|
存储 编译器 程序员
C语言:数据在内存中的存储
C语言:数据在内存中的存储
9 2
|
2天前
|
存储 编译器 C语言
C语言:字符函数 & 字符串函数 & 内存函数
C语言:字符函数 & 字符串函数 & 内存函数
10 2
|
4天前
|
Arthas 监控 Java
JVM工作原理与实战(三十一):诊断内存泄漏的原因
JVM作为Java程序的运行环境,其负责解释和执行字节码,管理内存,确保安全,支持多线程和提供性能监控工具,以及确保程序的跨平台运行。本文主要介绍了诊断内存溢出的原因、MAT内存泄漏检测的原理等内容。
11 0
|
4天前
|
存储 Arthas 监控
JVM工作原理与实战(三十):堆内存状况的对比分析
JVM作为Java程序的运行环境,其负责解释和执行字节码,管理内存,确保安全,支持多线程和提供性能监控工具,以及确保程序的跨平台运行。本文主要介绍了堆内存状况的对比分析、产生内存溢出的原因等内容。
10 0
|
4天前
|
Arthas Prometheus 监控
JVM工作原理与实战(二十九):监控内存泄漏的工具
JVM作为Java程序的运行环境,其负责解释和执行字节码,管理内存,确保安全,支持多线程和提供性能监控工具,以及确保程序的跨平台运行。本文主要介绍了解决内存溢出的步骤、Top命令、VisualVM、Arthas、Prometheus + Grafana等内容。
10 0
|
4天前
|
监控 Java 测试技术
JVM工作原理与实战(二十八):内存溢出和内存泄漏
JVM作为Java程序的运行环境,其负责解释和执行字节码,管理内存,确保安全,支持多线程和提供性能监控工具,以及确保程序的跨平台运行。本文主要介绍了内存溢出与内存泄漏、内存泄漏的常见场景、解决内存溢出的步骤等内容。
JVM工作原理与实战(二十八):内存溢出和内存泄漏
|
4天前
|
监控 安全 Java
JVM工作原理与实战(二十一):内存管理
JVM作为Java程序的运行环境,其负责解释和执行字节码,管理内存,确保安全,支持多线程和提供性能监控工具,以及确保程序的跨平台运行。本文主要介绍了不同语言的内存管理(C/C++、Java)、垃圾回收的对比(自动垃圾回收与手动垃圾回收)等内容。
11 0
|
4天前
|
Arthas 存储 监控
JVM工作原理与实战(二十):直接内存
JVM作为Java程序的运行环境,其负责解释和执行字节码,管理内存,确保安全,支持多线程和提供性能监控工具,以及确保程序的跨平台运行。本文主要介绍了直接内存、在直接内存上创建数据等内容。