![](https://img-blog.csdnimg.cn/20201014180756724.png?x-oss-process=image/resize,m_fixed,h_64,w_64)
C语言
bit_x
这个作者很懒,什么都没留下…
展开
-
引用计数
引用计数是这样一个技巧,它允许多个有相同值的对象共享这个值的实现。这个技巧有两个常用动机。第一个是简化跟踪堆中的对象的过程。一旦一个对象通过调用new被分配出来,最要紧的就是记录谁拥有这个对象,因为其所有者--并且只有其所有者--负责对这个对象调用delete。但是,所有权可以被从一个对象传递到另外一个对象(例如通过传递指针型参数),所以跟踪一个对象的所有权是很困难的。象auto_p转载 2010-05-12 16:53:00 · 701 阅读 · 0 评论 -
内存碎片产生原因及处理
<br /><br />内存碎片是一个很棘手的问题。如何分配内存决定着内存碎片是否会、何时会、如何会成为一个问题。<br /><br /> 即使在系统中事实上仍然有许多空闲内存时,内存碎片还会最终导致出现内存用完的情况。一个不断产生内存碎片的系统,不管产生的内存碎片多么小,只要时间足够长,就会将内存用完。这种情况在许多嵌入式系统中,特别是在高可用性系统中是不可接受的。有些软件环境,如 OSE 实时操作系统已经备有避免内存碎片的良好工具,但个别程序员做出的选择仍然会对最终结果形成影响。<br /> “碎片转载 2010-06-08 12:04:00 · 4271 阅读 · 0 评论 -
#pragma 和 内存对齐
<br /><br />什么是内存对齐? <br /> 先看下面的结构: <br /> struct TestStruct1 <br /> <br /> { <br /> <br /> char c1; <br /> <br /> short s; <br /> <br /> char c2; <br /> <br /> int i; <br /> <br /> }; <br /> <br /> 假设这个结构的成员在转载 2010-06-08 12:38:00 · 586 阅读 · 0 评论 -
引用与指针的比较
<br />来自:高质量c/c++编程<br />引用是C++中的概念,初学者容易把引用和指针混淆一起。一下程序中,n是m的一个引用(reference),m是被引用物(referent)。<br /> intm;<br /> int&n = m;<br />n相当于m的别名(绰号),对n的任何操作就是对m的操作。例如有人名叫王小毛,他的绰号是“三毛”。说“三毛”怎么怎么的,其实就是对王小毛说三道四。所以n既不是m的拷贝,也不是指向m的指针,其实n就是m它自己。<br />引用的一些规则转载 2010-06-07 10:32:00 · 528 阅读 · 0 评论 -
这题真缺德 --- 逗号表达式
<br />int main(void)<br />{<br />int a[3][2] = {(0,1), (2,3), (4,5)};<br />int *p = a[0];<br />printf("*p = %d/n", p[0]);<br />return 0;<br />}<br /> <br />输出不是0而是1.数组初始化时花括号里面嵌套了小括号(逗号表达式),此初始化相当于a[3][2] = {1, 3, 5};原创 2010-06-08 16:23:00 · 597 阅读 · 0 评论 -
二维数组 数组指针
<br />int a[5][5];<br />int (*p)[4];<br />p = a;<br />问 &p[4][2] - &a[4][2]等于多少?<br />画画图就知道了...<br /> <br />原创 2010-06-08 16:40:00 · 481 阅读 · 0 评论 -
不用任何变量实现strlen()函数
<br /><br />用递归函数解决这个问题<br />1、<br />int __strlen( char *str_source)<br />{<br />assert( NULL == str_source );<br />if ( '/0' == *str_source)<br />{<br />return 0 ;<br />}<br />else<br />{<br />return ( 1 + __strlen( ++str_source ) );<br />}<br />}<br /> <原创 2010-06-08 18:35:00 · 631 阅读 · 0 评论 -
c语言全局变量的忠告 c语言存储类说明符
1) 所有全局变量全部以g_开头,并且尽可能声明成static类型. 2) 尽量杜绝跨文件访问全局变量.如果的确需要在多个文件内访问同一变量,应该由该变量定义所在文件内提供GET/PUT函数实现. 3) 全局变量必须要有一个初始值,全局变量尽量放在一个专门的函数内初始化. 4) 如调用的函数少于三个,请考虑改为局部变量实现. 存储类说明符:Auto:只在块内变量声明中被允许, 表示变量具有本地生存期.Extern:出现在顶层或块的外部变量函数与变量声明中,表示声明的对象具有静态生存期, 连接程序知道其名字.原创 2010-06-09 10:16:00 · 3494 阅读 · 0 评论 -
C语言实现类中方法 用函数指针在结构体中加入函数
<br />/********* first.h *********/#ifndef __FIRST__H_H#define __FIRST__H_H//打开TYPE__A 或 TYPE__B的作用是相同的//#define TYPE__A#define TYPE__Bchar *my_get_char(char *str);int my_get_int(int in);#ifdef TYPE__Astruct test_st{ int elem; char*原创 2010-06-09 13:11:00 · 6805 阅读 · 0 评论 -
C++位操作技巧
一、注意事项:a、与:&,两位都为1,才为1;b、或:|,两位都为0,才为0;c、微操作只能用于整形数据,float和double进行位操作时编译器会报错;d、异或:^,两位相同为0,不同为1;e、取反:~,1变为0,0变为1;f、左移:g、右移:>>,各二进制全部向右移位,对于无符号数,低位丢失,高位补零;有符号数个编译器不同,有的补符号位,有的补0;二、技巧用途原创 2013-10-17 15:36:53 · 2536 阅读 · 0 评论 -
网络套接字socket
一、socket建立的客户端和服务器端图示:二、注意事项:1、大小端:因为不知道发送端机器使用的字节序是否和接收端机器使用的字节序相同,所以发送前都将其转换为网络字节序(大端字节序),接受时在讲网络字节序转换为本机字节序。发送端:在发送非字符串的类型(如整型)时,要注意在发送前使用htonl或者htons将其本机字节序(可能大端,也可能小端)转换为网络字原创 2013-11-13 10:49:26 · 1555 阅读 · 0 评论 -
socket epoll 模型
/* * File: main.c * Author: xys * * Created on 2013年12月12日, 下午3:14 * * 实现功能:通过epoll,处理多个socket请求 * 监听一个端口,监听到有链接时,添加epoll_event * * 命令行下 telnet localhost 3304 */#include #include #i原创 2013-12-12 18:13:23 · 3354 阅读 · 0 评论 -
#pragma
<br />在所有的预处理指令中,#pragma 指令可能是最复杂的了,它的作用是设定编译器的状态或者是指示编译器完成一些特定的动作。<br />#pragma指令对每个编译器给出了一个方法,在保持与C和C++语言完全兼容的情况下,给出主机或操作系统专有的特征。<br />依据定义,编译指示是机器或操作系统专有的,且对于每个编译器都是不同的。 <br /> 其格式一般为: #pragma para <br /> 其中para为参数,下面来看一些常用的参数。 <br /> <br />转载 2010-06-08 11:44:00 · 501 阅读 · 0 评论 -
volatile
<br />一个定义为volatile的变量是说这变量可能会被意想不到地改变,这样,编译器就不会去假设这个变量的值了。精确地说就是,优化器在用到这个变量时必须每次都小心地重新读取这个变量的值,而不是使用保存在寄存器里的备份。下面是volatile变量的几个例子: <br /> 1). 并行设备的硬件寄存器(如:状态寄存器) <br /> 2). 一个中断服务子程序中会访问到的非自动变量(Non-automatic variables) <br /> 3). 多线程应用中被几个任务共享的变量转载 2010-06-07 14:56:00 · 967 阅读 · 0 评论 -
静态存储区、堆和栈的区别((转)类似的东西已经被转过无数次了)
一、预备知识—程序的内存分配 一个由C/C++编译的程序占用的内存分为以下几个部分 1、栈区(stack)— 由编译器自动分配释放 ,存放函数的参数值,局部变量的值等。其 操作方式类似于数据结构中的栈。 2、堆区(heap) — 一般由程序员分配释放, 若程序员不释放,程序结束时可能由OS回 收 。注意它与数据结构中的堆是两回事,分配方式倒是类似于链表,呵呵。 3、全局区(静态区)(static)—,全局变量转载 2010-06-04 11:30:00 · 480 阅读 · 0 评论 -
typedef的四个用途和两个陷阱
用途一: 定义一种类型的别名,而不只是简单的宏替换。可以用作同时声明指针型的多个对象。比如: char* pa, pb; // 这多数不符合我们的意图,它只声明了一个指向字符变量的指针, // 和一个字符变量; 以下则可行: typedef char* PCHAR; // 一般用大写 PCHAR pa, pb; // 可行,同时声明了两个指向字符变量的指转载 2010-05-28 09:36:00 · 440 阅读 · 0 评论 -
可重入和不可重入
这种情况出现在多任务系统当中,在任务执行期间捕捉到信号并对其进行处理时,进程正在执行的指令序列就被信号处理程序临时中断。如果从信号处理程序返回,则继续执行进程断点处的正常指令序列,从重新恢复到断点重新执行的过程中,函数所依赖的环境没有发生改变,就说这个函数是可重入的,反之就是不可重入的。众所周知,在进程中断期间,系统会保存和恢复进程的上下文,然而恢复的上下文仅限于返回地址,cpu寄存器等之类的少量上下文,而函数内部使用的诸如全局或静态变量,buffer等并不在保护之列,所以如果这些值在函数被中断期间发生了改转载 2010-06-01 14:45:00 · 368 阅读 · 0 评论 -
编写可移植性c程序的要点
1.分层设计,隔离平台相关的代码。就像可测试性一样,可移植性也要从设计抓起。一般来说,最上层和最下层都不具有良好的可移植性。最上层是GUI,大多数GUI都不是跨平台的,如Win32 SDK和MFC。最下层是操作系统API,大多部分操作系统API都是专用的。 如果这两层的代码散布在整个软件中,那么这个软件的可植性将非常的差,这是不言自明的。那么如何避免这种情况呢?当然是分层设计了: 最底层采用Adapter模式,把不同操作系统的API封装成一套统一的接口。至于封装成类还是封装成函数,要看你采用的C还是C+转载 2010-06-01 15:50:00 · 1659 阅读 · 0 评论 -
结构体中位域存储
struct s1 { int i: 8; int j: 4; int a: 3; double b; }; printf("sizeof(s1)= %d/n", sizeof(s1)); 求输出结果. 答案:16 下面是解释: 理论上是这样的,首先是i在相对0的位置,占8位一个字节,然后,j就在相对一个字节 的位置,由于一个位置的字节数是4位的倍数,因此不用对齐,就放在那里了,然后是 a,要在3位的倍数关系的位置上,因此要移一位,在15位的位置上放下,目前总共是18 位,折算过来是2字节2位的样子,由于d转载 2010-06-02 14:39:00 · 971 阅读 · 0 评论 -
编译器进行符号扩展
typedef struct{ int a:2; int b:2; int c:1;}test;main(){ test t; t.a = 1; t.b = 3; t.c = 1; cout原创 2010-06-02 15:59:00 · 683 阅读 · 0 评论 -
对无符号类型的建议(C/C++)
尽量不要在你的代码中使用无符号整数,以免增加不必要的复杂性。尤其是,不要仅仅因为无符号数不存在负数(如年龄,国债)而用它来表述数量。 尽量使用像int那样的有符号整数,这样在涉及升级混合类型的复杂细节时,不必担心边界情况(如-1被翻译成很大的正数)。只有在使用位段和二进制掩码时,才可以使用无符号数。应该在表达式中使用强制类型转换,使操作数均为有符号数或无符号数,就不必让编译器选择结果的类型。原创 2010-06-01 14:30:00 · 649 阅读 · 0 评论 -
C语言编译全过程
C语言编译全过程 编译的概念:编译程序读取源程序(字符流),对之进行词法和语法的分析,将高级语言指令转换为功能等效的汇编代码,再由汇编程序转换为机器语言,并且按照操作系统对可执行文件格式的要求链接生成可执行程序。 编译的完整过程:C源程序-->预编译处理(.c)-->编译、优化程序(.s、.asm)-->汇编程序(.obj、.o、.a、.ko)-->链接程序(.exe、.elf、.axf等)1. 编译预处理 读取c源程序,对其中的伪指令(以#开头的指令)和特殊符号进行处理转载 2010-06-01 15:09:00 · 401 阅读 · 0 评论 -
c语言面试题
1.引言 本文的写作目的并不在于提供C/C++程序员求职面试指导,而旨在从技术上分析面试题的内涵。文中的大多数面试题来自各大论坛,部分试题解答也参考了网友的意见。 许多面试题看似简单,却需要深厚的基本功才能给出完美的解答。企业要求面试者写一个最简单的strcpy函数都可看出面试者在技术上究竟达到了怎样的程度,我们能真正写好一个strcpy函数吗?我们都觉得自己能,可是我们写出的strcpy很可能只能拿到10分中的2分。读者可从本文看到strcpy函数从2分到10分解答的例子,看看自己属于什么样的层次。转载 2010-06-01 15:16:00 · 880 阅读 · 0 评论 -
c语言交换两个整数值的错误
看看下面的一段程序有什么错误: swap( int* p1,int* p2 ){int *p;*p = *p1;*p1 = *p2;*p2 = *p;}在swap函数中,p是一个“野”指针,没有初始化的情况下它有可能指向系统区,像这样强制赋值,可能导致程序运行的崩溃。不可强制赋值,p = NULL后更不行,p没指向任何东西,它不可能有*p操作的在。VC++中DEBUG运行时提示错误“Access Violation”。该程序应该改为:原创 2010-06-03 17:02:00 · 840 阅读 · 0 评论 -
memset用法详解(转)
memest原型 (please type "man memset" in your shell) void *memset(void *s, int c, size_t n); memset:作用是在一段内存块中填充某个给定的值,它对较大的结构体或数组进行清零操作的一种最快方法。常见的三种错误第一: 搞反了c 和 n的位置. 一定要记住 如果要把一个char a[20]清零, 一定是 memset(a, 0, 20) 而不是 memset(a, 20, 0) 第二: 过度使用转载 2010-06-04 10:51:00 · 481 阅读 · 0 评论 -
大小端
所谓的大端模式,是指数据的低位(就是权值较小的后面那几位)保存在内存的高地址中,而数据的高位,保存在内存的低地址中,这样的存储模式有点儿类似于把数据当作字符串顺序处理:地址由小向大增加,而数据从高位往低位放; 所谓的小端模式,是指数据的低位保存在内存的低地址中,而数 据的高位保存在内存的高地址中,这种存储模式将地址的高低和数据位权有效地结合起来,高地址部分权值高,低地址部分权值低,和我们的逻辑方法一致。 为什么会有大小端模式之分呢?这是因为在计算机系统中,我们是以字节为单位的转载 2010-06-04 15:14:00 · 1469 阅读 · 0 评论 -
database is locked和SQLITE_BUSY
这是官方文档:http://www.sqlite.org/cvstrac/wiki?p=DatabaseIsLocked下面我做了几个实验:1、多个线程(pthread),使用同一个句柄(一次sqlite3_open,同一个数据库文件),在多个线程中同时使用此句柄,这些线程中有的是进行select操作的,有的是进行update操作的,使用的都是sqlite3_exec函数;结果是没原创 2014-01-22 15:53:34 · 14404 阅读 · 2 评论