在C中判断变量存储类型(字符常量/数组/动态变量)

在chinaunix论坛上有人问到关于变量存府类型的问题,我觉得可以写个测试代码加深大家对内存使用和布局的理解。下面我把原问题及处理办法贴出来,限供大家参考。

原问题:

static
void testB (char *src)
{
/* 判断传入的src 是属于 @1/2/3 ??? */
do_somthing ();
} static
void testA (char *src)
{
char *a = "hello world";
char b[100] = "hello world"; testB (a); /* @1 */
testB (b); /* @2 */
testB ("hello world" ); /* @3 */
}

@1 有名常量
@2 缓冲资源
@3 未名常量

怎么用宏去区别啊???

下面是对这个问题的处理办法:

编译器和语言并没有直观的提供什么功能去实现这个处理,可以换个思路,在C中有四个存储类型static,automatic,register,dynamic。每种类型的存储的地址都是可识别的,通过对存储地址的判断可以识别实事的变量或常量变型。
char *a = "hello world";testB (a); 和 testB ("hello world" );  这两个调用实际上是一样的。编译器在处理的时候会把对hello world的变引指向相同的地方(编译器基本都这么进行优化处理,不属于标准规定)。根据上述说法那下面的公式成立:编译器对常量变量的内存处理策略+操 作系统的内存布局=可明确定位的内存识别。由于操作系统的内存布局因系统而定,编译器的实现也各有不同,所以就算得出结论要实现相关处理的代码也是很难进 行移植的。下面是完成相关功能的代码在linux下测试通过。

#include <stdlib.h>
#include <stdio.h>
#include <string.h> int global_dummy = 0;
static
void testB (char *src)
{
/* 判断传入的src 是属于 @1/2/3/4*/
int local_dummy = 0;
if( (unsigned long)src < (unsigned long )&local_dummy ){
//if( src > testB ){
if( (unsigned long )src < (unsigned long )&global_dummy ){
printf("string literal\n\n");
}
else if ( (unsigned long ) src > (unsigned long ) &global_dummy){
printf("malloc string\n\n");
}
//}
}
else
{
printf("array: stack\n\n");
}
}
static
void testA ()
{
char *a = "hello world";
char b[100] = "hello world";
char *c = malloc(100);
strcpy(c,a);
printf("char *a = \"hello world\";\n");
testB (a); /* @1 */
printf("char b[100] = \"hello world\";\n");
testB (b); /* @2 */
printf(" (\"hello world\" )\n");
testB ("hello world" ); /* @3 */
printf("char *c = malloc(100);\n");
testB (c ); /* @4 */
free(c);
} int main(int argc,const char** argv)
{
testA();
return 0;
}

程序的运行结果如下:
char *a = "hello world";
string literal

char b[100] = "hello world";
array: stack

("hello world" )
string literal

char *c = malloc(100);
malloc string

虽然没有处理和测试所有情况,但以述代码我觉得针对理解内存布局和变量使用问题已经足够了。

下面贴个linux下程序运行的内存布局图,可以加深对上述代码的理解

ps:这不是抄袭,是原创

 
 
 
标签: 内存布局

在C中判断变量存储类型(字符常量/数组/动态变量)的更多相关文章

  1. python中判断变量的类型

    python的数据类型有:数字(int).浮点(float).字符串(str),列表(list).元组(tuple).字典(dict).集合(set) 一般通过以下方法进行判断: 1.isinstan ...

  2. JavaScript中判断变量类型最简洁的实现方法以及自动类型转换(#################################)

    这篇文章主要介绍了JavaScript中判断整字类型最简洁的实现方法,本文给出多个判断整数的方法,最后总结出一个最短.最简洁的实现方法,需要的朋友可以参考下 我们知道JavaScript提供了type ...

  3. 【react】利用prop-types第三方库对组件的props中的变量进行类型检测

    1.引言--JavaScript就是一个熊孩子   1.1对于JSer们来说,js是自由的,但同时又有许多让人烦恼的地方.javascript很多时候就是这么一个熊孩子,他很多时候并不会像C和java ...

  4. Js中判断变量存不存在的问题

    前面写过jquery对象存在与否的判断.现在谈下Js中判断变量存不存在的问题. 如果这样if(!a),当变量a在js中没有申明时,就会报错,那么接下去的代码将不会被执行.注意,这种判断只要变量申明过, ...

  5. JavaScript中判断整字类型最简洁的实现方法

    这篇文章主要介绍了JavaScript中判断整字类型最简洁的实现方法,本文给出多个判断整数的方法,最后总结出一个最短.最简洁的实现方法,需要的朋友可以参考下 我们知道JavaScript提供了type ...

  6. prop-types:该第三方库对组件的props中的变量进行类型检测

    利用prop-types第三方库对组件的props中的变量进行类型检测

  7. Python如何判断变量的类型

    Python判断变量的类型有两种方法:type() 和 isinstance() 如何使用 对于基本的数据类型两个的效果都一样 type() ip_port = ['219.135.164.245', ...

  8. js中判断对象具体类型

    大家可能知道js中判断对象类型可以用typeof来判断.看下面的情况 <script> alert(typeof 1);//number alert(typeof "2" ...

  9. C语言支持的四种变量存储类型

    http://blog.csdn.net/zhandoushi1982/article/details/5425835 一)auto:auto称为自动变量(局部变量).局部变量是指在函数内部说明的变量 ...

随机推荐

  1. js 里面 写 C# 代码 遇到的问题

    js  代码块 必须放置在 body 里面

  2. java设计模式之三单例模式(Singleton)

    单例对象(Singleton)是一种常用的设计模式.在Java应用中,单例对象能保证在一个JVM中,该对象只有一个实例存在.这样的模式有几个好处: 1.某些类创建比较频繁,对于一些大型的对象,这是一笔 ...

  3. Oracle 11g sys,system 密码忘记设置解决办法

    原文:Oracle 11g sys,system 密码忘记设置解决办法 1.启动sqlplus 2.请输入用户名:  sqlplus/as sysdba 3.输入口令: 直接回车 4.连接到: Ora ...

  4. windows下 composer常见问题及处理

    错误一: Warning: This development build of composer is over 30 days old. It is recommend ed to update i ...

  5. [译]JDK 6 and JDK 7中的subString()方法

    (说明,该文章翻译自The substring() Method in JDK 6 and JDK 7) 在JDK 6 and JDK 7中的substring(int beginIndex, int ...

  6. 通过如何通过js实现复制粘贴功能

    在ie中window.clipboardData(剪切板对象)是可以被获取,所以利用这个方法我们可以实现在IE当中复制粘贴的功能,demo如下! <html> <head> & ...

  7. 使用javaservice 将jboss 注册为服务

    近来做项目,需要jboss定期重新启动.不想再看到jboss启动那个黑洞洞的窗口,就想着把它注册为服务,然后在net start.恰好objectweb上有个open source的javaservi ...

  8. openGL线s的绘制

    /** * 缓冲区工具类 */ public class BufferUtil { /** * 将浮点数组转换成字节缓冲区 */ public static ByteBuffer arr2ByteBu ...

  9. go orcale

    golang连接orcale   使用glang有一段时间了,最开始其实并不太喜欢他的语法,但是后来熟悉之后发现用起来还挺爽的.之前数据库一直使用mysql,连接起来没有什么问题,github上有很多 ...

  10. POCO Controller

    ---恢复内容开始--- POCO Controller 你这么厉害,ASP.NET vNext 知道吗?   写在前面 阅读目录: POCO 是什么? 为什么会有 POJO? POJO 的意义 PO ...