manbetx官方网站

MONO 如何打包 .NET程序独立运作(winform篇)13 重忆C 之 工程开发命令。

十月 7th, 2018  |  manbetx官方网站

.NET程序独立运行是恃运行.NET的处理器及,不需要安装.NET框架。

pwd
回到了干净目录

.NET程序集“独立运转”并非真正的单身,它是运行于mono运行时基础之上的。由于这运行时可以独自在,所以,我们无待以靶机上安装.NET框架。

这时候看到网返回了一个 /,这个 / 被我们称为系统的
根目录(root),这个职位吗即是咱本于系受之职务。

opebet体育app 1

但是,我们设进行工作之职位的路径为:

 

/home/user/project

 

因而,我们只要学会如何切换我们所在的岗位:

如上图:

输入 cd 命令,并在 cd 命令后增长空格,在之后输入进行工作之职的路子:

 

cd /home/user/project

平等,嵌入或不嵌入.NET程序集的故C/C++语言写的主程序,这个主程序负责对mono运行时进行操作。同时还可配合.NET完成其余的天职(比如提供函数供.NET使用);

随即就算是一个层级化路径,其实该可经过

 

cd home
cd user
cd project

仲,mono的.NET运行时,这是一个动态库文件(mono又提供了静态库),是.NET程序集运行的重要条件。

逐次到达。

 

下载输入 ls -l。
这边虽发出只old目录。

其三,MONO运行时之配备文件或者文件夹(并不一定需要)。

opebet体育app 2

 

image.png

季,外部的主次集并未放置至C程序中之别的相互关.NET程序集。

mv main.c old             //mv [选项] 源文件或目录 目标文件或目录

“独立运转”的过程是:

双重运移动操作:

C语言通过mono提供的运转时api,调用mono运行时有关函数,通过mono运行时加载并运行.NET程序。

opebet体育app 3

 

移动文件

即:

更创新文件,通过命令

C语言程序(your.exe)
–à mono的.NET运行时(libmonosgen-2.0.dll) –à .NET程序集

touch main.c 

 

创建新文件
此刻可以望见:

libmonosgen-2.0.dll,即是.NET程序集的运行规则,也是.NET程序集与C程序之间数据交流、函数互调的大桥。

opebet体育app 4

哼了,有矣上述之理论知识,下面我们就算起实施一下咔嚓

创建文件

 

old目下将key删除

1.施用Xbuid命令编译

opebet体育app 5

opebet体育app 6

删除“`key“`文件

 

复多系命令的但叠加参数和动意义,可以经
man [空格] [命令名]的法展开进行更为的询问(查询后脱离只需要敲击键盘上的
q 即可)。

2.把编译后的net 运行文件 写副到一个 char[]变量中,并记下是序集的称,大小

还多复杂的命令,点击这里

mkpack H:\Csharp\Mono\Test\TestBuild\TestBuild\WindowsFormsApplication1\bin\Debug\WindowsFormsApplication1.exe

基本上模块程序

之前的课中,所有文件操作都是就文件进行。对于一个特就一个特定的职责,只包含十几只函数的次序来说,单文件的团组织章程还算是可以领,但是当次更为长,程序实现的成效更多,将他们整个且集体以一个文本里虽见面更换得不那么容易被人收受了。

就此,我们要学习怎么样当 C
语言中将不同功能以差不多个代码文件中分别实现,然后以它当做多只模块组织于并呢同一个次服务。


会生成3个文件

关于gcc命令

原地址:gcc命令中参数c和o混合使用的详解、弄清gcc test.c 与 gcc -c
test.c
的差别

gcc命令使用GNU推出的冲C/C++的编译器,是开放源代码领域用最广大的编译器,具有功能强大,编译代码支持性优化等特性。现在无数程序员都使用GCC,怎样才能更好的采用GCC。目前,GCC可以据此来编译C/C++、FORTRAN、JAVA、OBJC、ADA等语言的先后,可根据需要选择设置支撑的语言。

语法

gcc(选项)(参数)

选项

-o:指定生成的出口文件;
-E:仅执行编译预处理;
-S:将C代码转换为汇编代码;
-wall:显示警告信息;
-c:仅执行编译操作,不进行连接操作。

参数

C源文件:指定C语言源代码文件。

实例
常用编译命令选项

借用设源程序文件称吧test.c

无选项编译链接

gcc test.c

test.c先行处理、汇编、编译并链接形成可执行文件。
此处不指定输出文件,默认输出为a.out

选项 -o

gcc test.c -o test

test.c预先处理、汇编、编译并链接形成可执行文件test
-o分选用来指定输出文件的文件称。

选项 -E

gcc -E test.c -o test.i

用test.c预处理输出test.i文件。

选项 -S

gcc -S test.i

拿优先处理输出文件test.i汇编成test.s文件。
选项 -c

gcc -c test.s

以汇编输出文件test.s编译输出test.o文件。

无选项链接

gcc test.o -o test

拿编译输出文件test.o链接成最终可执行文件test。

选项 -O

gcc -O1 test.c -o test

应用编译优化级别1编译程序。级别为1~3,级别越充分优化作用更好,但编译时间越长。

多源文件之编译方法

倘产生差不多只来文件,基本上有三三两两种编译方法:

一经来星星点点个来自文件呢test.ctestfun.c

  • 差不多单文件并编译

gcc testfun.c test.c -o test

testfun.ctest.c分别编译后链接成test可执行文件。

  • 个别编译各个源文件,之后对编译后输出的目标文件链接。

gcc -c testfun.c

将testfun.c编译成testfun.o

gcc -c test.c

将test.c编译成test.o

gcc -o testfun.o test.o -o test

将testfun.o和test.o链接成test

以上两种植艺术相较,第一中方法编译时需要具有文件又编译,而第二栽方法可以独自更编译修改的文书,未修改的文本不用还编译。


再也来复习一下:

gcc -c a.c 编译成靶子文件a.o

gcc -o a a.o 生成执行文书a.exe

gcc a.c 生成执行文书a.exe

gcc -o a -c a.c 编译成靶子文件a

gcc -o a a.c 生成执行文书a.exe

于a.c中援test.c中之一个函数后:

gcc -c test.c 编译成靶子文件test.o

gcc -c a.c 编译成靶子文件a.o

gcc -o a test.o a.o 生成执行文书a.exe

gcc -o a test.o a.c 生成执行文书a.exe

gcc -o a test.c a.c 生成执行文书a.exe

gcc -o a test.o a.c 生成执行文书a.exe

总结:只要参数中产生-c,总是变目标文件;只要参数中无-c而只有-o,则连接变执行文书。


当刚起念 C
语言的早晚,我们曾学习过,当我们的先后只发生一个main.c文本时,我们得以在命令行中通过

gcc -o program main.c

针对单个代码文件进行编译,生成可执行文件program,并且经过./program运转编译生成的先后。在咱们之前的课被,计蒜客的上学系统为帮助您进行了这般的操作。

对待于单个文件、单一功能的顺序,当次来差不多个模块时,问题便开变得复杂了。我们针对各级一个模块会首先编译出每个模块对应之*.o目标代码文件(relocatable
object file),例如:

gcc -c -o set.o set.c

会见用我们的一个set.c文本编译成一个set.o的目标代码文件。请小心,这里的-c表示生成目标代码文件。-o与事先才文件的下同样,在它们后咱们会写清楚为扭转的文件之称。

当我们做到了各国一个独门模块的编译并取得它的目标代码文件后,我们可以拿我们的主程序的靶子代码文件以及她们链接以同步。例如:

gcc -o program main.o set.o others.o

以对象代码文件set.oothers.omain.o每当链接以联名,并且输出了
可执行文件(excutable file)program。

咱照样得以经过./program运作编译生成的次第。

当我们将一个主次写在多单文件被时,每一个文书中之变量和函数默认都是只有文件内之一部分才方可看的。但是发生一对奇异的全局变量、类型定义、函数可能会见要以差不多独文件被让利用。

这会儿,我们可以立即看似的情节单独写成一个 头文件(header
file),并且用全局变量、类型定义、函数声明写到头文件中。

对一个文书set.c,习惯及其的峰文件会让命名吧set.h。在有着需要因此set.h中全局变量、类型定义、声明的函数的文书中,用

#include "set.h"

拿相应之条文件引入。在这边的引入头文件措施与引入系统库头文件之艺术要命相近,只不过这里用之凡引号""如休是尖括号<>

由于头文件里呢得以引入头文件,因此我们或实际多次引入和一个文件,比如我们引1.h2.h,且1.h也引入2.h,这时坐2.h于引入了片坏,就闹或出现重的扬言。为了化解这题目,我们2.h中定义一个特大,在2.h的极其开头判断这大是否被定义了,如果给定义了,就跨越了2.h整个文件之情节。

这边我们拿会为此到一定量个新的先处理指令#ifndef xxx#endif,它们成为对出现还#ifndef当头里,作用是如果此时并未曾定义xxx宏,则这对#ifndef xxx,
#endif中的始末中。(其中xxx可以轮换为随意宏名)

这样```2.h```可以写为类似于如下的内容:
#ifndef xxx
#define xxx
typedef enum Status { Success, Fail };
typedef struct {
    char *name;
    int age;
} People;
Status go_to_Jisuanke(People);
#endif

细的同班曾发现,如果当先后中莫引入2.h的职务定义了xxx宏,则#include "2.h"未遭之扬言并无见面给引入,因此我们无该以此采取xxx这种平凡的讳。实际上,我们一般会使用一个跟峰文件称相关的名来代表xxx,比如一个常用的代码风格里,这个庞然大物的名形式为工程名_路径名_文件名_H_

opebet体育app 7

小结的几碰

  • 某个一样代码中定义之函数如果用吃另外代码文件所采用,应该将函数的宣示放入头文件,并在外代码文件中引入这无异于头文件。
  • 并不需要把每个函数单独写成一个模块,还是当因功能的细分和实现去控制怎么抽出模块。
  • 得只有多个.c的公文,也并不一定非要是还拆出.h文件。
  • #include足叫用来引入系统库头文件也足以让用来引入自己实现之条文件。
  • 只不过在引入系统库头文件时,我们数会用尖括号<>,而以引入自己实现的头文件时相似用引号""
  • gcc时,-o自此写的凡浮动可执行文件的称呼。-c的参数的动会帮助我们取得一个对象文件。

//-c和-o都是gcc编译器的可选参数

//-c表示只编译(compile)源文件但不链接,会把.c或.cc的c源程序编译成目标文件,一般是.o文件。
//-o用于指定输出(out)文件名。不用-o的话,一般会在当前文件夹下生成默认的a.out文件作为可执行程序。

//例如
gcc -c test.c          //将生成test.o的目标文件
gcc -o app test.c           //将生成可执行程序app

gcc -c a.c -o a.o          //表示把源文件a.c编译成指定文件名a.o的中间目标文件(其实在这里,你把-o a.o省掉,效果是一样的,因为中间文件默认与源文件同名,只是后缀变化)。

data.c 是.NET程序集的二进制内容

Makefile

在头里学习多模块程序的时,我们得事先拿每个模块的代码都很成为目标代码文件,然后再度以目标代码文件联编成一个可执行文件。如果各国一样潮编译都使输入这么多命令,是未是很复杂呢?如果老是修改一点点情节即得再次编译整个工程,是休是颇浪费时间呢?

为化解所遇到的题目,方便开发,我们用一个叫make的指令,它可以读取Makefile文本,并且根据Makefile遇的条条框框描述把自文件充分成为可实施的主次文件。

最中心的Makefile中寓了同多重形式如下的平整。请留心,每一样久规则之通令前,必须使来一个制表符\t。

目标: 依赖1 依赖2 ...
    命令

如,可以形容一长条规则:

array.o: array.c array.h
   gcc -c -o array.o array.c

表示生成的文本是目标代码文件array.o,它借助让array.carray.h
当我们在命令行中执行make array.o时常,根据当时无异平整,如果array.o未设有或者array.carray.h足足有比array.o更新,就见面实行gcc -c -o array.o array.c

咱们将上述代码保存也Makefile,与array.carray.h身处同等目录,在很目录里行make array.o即可知顾效果。

注意:Makefile里之除当前目录隐藏文件外的首先独对象会成运行make未指定目标时的默认目标。

再看:

main: array.o main.o
    gcc -o main array.o main.o

main.o: main.c array.h
    gcc -c -o main.o main.c

array.o: array.c array.h
    gcc -c -o array.o array.c

Makefile出多长长的规则时,如果我们意在就生成中一个,我们好在make命令后长要变更的目标的名号。例如,在此地我们得以实施make main.omake array.omake main。当我们实施make main时,make命发现array.omain.o勿存,就会因盖其啊对象的规则先生化作其。

不少时分,会用将.o为后缀的目标代码文件及可实施之次第文件去,完全从头进行编译。那么我们可以描绘一条clean规则,例如:

clean:
    rm -f array.o main.o main

rm指令表示去文件,-f意味着强制,因此rm -f array.o main.o main

遵预期,当我们实践make clean不怕可去除array.omain.omain了。事实确实如此也?

因为毕竟这如就是clean文件,rm令就不见面实施了。为了解决是题材,我们透过一个独特的计告诉make夫名为也clean的规则以clean存在的早晚还有效。

.PHONY: clean

clean:
    rm -f array.o main.o main

.PHONY用于声明一些地下目标,伪目标与一般的目标的基本点分是伪目标不见面给检查是不是是被文件系统中若默认不设有且不见面使用默认规则变化它。

于Makefile中我们还得下其的变量和注释。

# 井号开头的行是一个注释
# 设置 C 语言的编译器
CC = gcc

# -g 增加调试信息
# -Wall 打开大部分警告信息
CFLAGS = -g -Wall

# 整理一下 main 依赖哪些目标文件
MAINOBJS = main.o array.o

.PHONY: clean

main: $(MAINOBJS)
    $(CC) $(CFLAGS) -o main $(MAINOBJS)

array.o: array.c array.h
    $(CC) $(CFLAGS) -c -o array.o array.c

main.o: main.c array.h
    $(CC) $(CFLAGS) -c -o main.o main.c

clean:
    rm -f $(MAINOBJS) main

点这个事例已经是一个较为完好的Makefile了。以#启的凡咱们的笺注,我们以此间用注释说明了我们定义的Makefile变量的用。CC变量定义了编译器,CFLAGS变量标记了编译参数,MAINOBJS变量记录了main仰的靶子文件。定义之变量可以一直通过$(变量名)拓展下。

data_.c 是为文件用户调用的对准data.c的函数和变量

总结

  • 一个 Makefile
    可以蕴涵多个规则,我们既然好每次在make后证实履行哪个意义,也可经过定义之all来执行同样名目繁多的平整。
  • 每当用gcc编译时加上-Wall会显示错误信息,Wall是用于展示多数警戒信息的,编译错误信息默认就会来得。
  • Makefile其实描述了同多元转为对象文件、联编的过程,不使用make也是足以得的。
  • Makefile中的变量是用$()的法来用哒。

data.h  是data_.c的峰文件,是用户c源码必须的。

Makefile体验

opebet体育app 8

(1)

→ ~/project ls -l                                                                                 

total 16                                                                                          
-rw-r--r-- 1 user user 304 Sep 15 16:46 array.c                                                   
-rw-r--r-- 1 user user  87 Sep 15 16:46 array.h                                                   
-rw-r--r-- 1 user user 297 Sep 15 16:46 main.c                                                    
-rw-r--r-- 1 user user   0 Sep 15 16:46 main.h                                                    
-rw-r--r-- 1 user user 419 Sep 15 16:46 Makefile                                                  
→ ~/project                                                                                       
→ ~/project cat Makefile                                                                          

# 设置 C 语言的编译器                                                                             
CC = gcc                                                                                          

# -g 增加调试信息                                                                                 
# -Wall 打开大部分警告信息                                                                        
CFLAGS = -g -Wall                                                                                 

# 整理一下 main 依赖哪些目标文件                                                                  
MAINOBJS = main.o array.o                                                                         

.PHONY: clean                                                                                     

main: $(MAINOBJS)                                                                                 
        $(CC) $(CFLAGS) -o main $(MAINOBJS)                                                       

array.o: array.c array.h                                                                          
        $(CC) $(CFLAGS) -c -o array.o array.c                                                     

main.o: main.c array.h                                                                            
        $(CC) $(CFLAGS) -c -o main.o main.c                                                       

clean:                                                                                            
        rm -f $(MAINOBJS) main                                                                    
→ ~/project                                                                                      

opebet体育app 9

(2)

→ ~/project make                

gcc -g -Wall -c -o main.o main.c                                                  
gcc -g -Wall -c -o array.o array.c                                    
gcc -g -Wall -o main main.o array.o                                     
→ ~/project                               

opebet体育app 10

(3)

→ ~/project ./main              

1 2 3 4 5 6 7 8 9 0                                     
数组元素和为: 45                                             
数组元素平均值为: 4.5                                      

→ ~/project                                                 

opebet体育app 11

(4)

→ ~/project make clean                   

rm -f main.o array.o main             

opebet体育app 12

(5)

→ ~/project            
→ ~/project ls -l     

total 16                                             
-rw-r--r-- 1 user user 304 Sep 15 16:46 array.c          

 

指令执行参数

之前,main函数一般都不曾参数,对诺于运行时,一般就直输入而尽的主次文件称(例如./main)。

只是实在main函数可以起参数。我们好将另外过去无参数的main函数替换成下面这种有参数的main函数(不过考虑到我们连没有用,不写是怪健康的)。

int main(int argc, char **argv) {
    // ...
}

在这里,main函数有星星点点只参数,第一独参数是整数型,会流传命令执行参数的个数,程序运行时即便得收到。第二只参数是char **,其中存储了用户从命执行传递进入的参数。

倘若我们的次第可执行文件名也main,则于指令执行被输入./main hello world俺们见面得argc3argv[0]./mainargv[1]helloargv[2]world。如果起更多参数为足以因此类推。

命执行参数默认都是空格分隔,但是倘若我们希望包含空格的一个字符串作为参数,我们虽需以输入参数时用引号将其包装起来。

如我们的主次可执行文件名吧main,则于指令执行吃输入./main "hello world" is my greet我们见面收获argc5argv[0]./mainargv[1]hello worldargv[2]isargv[3]myargv[4]greet

别被接纳至之argv参数都得吃看成正常的字符串在代码里下。在不少主次的计划性着,我们见面要根据接收到的参数来决定程序的履措施,这时候,学会用argcargv就是显示非常重要了。在以后的课中,你也会见用采用当下同片的学识,一定要学明白喔。

3.以编译data.c编译为对象文件data.o

部分总

  • 指令执行读入的参数是起命行键入的可执行程序路径始于算计。
  • 以main函数中用来接收命令行参数的函数参数中,第一独凡是命令执行参数的个数。
  • 在int main(int argc, char **argv)中,argc就稳定啊 2
    了,它拿走到之当是命令执行被键入的参数个数。

gcc -c -o data.o data.c

命令执行参数

指令执行参数是怎么抱与动用的?

吁先输入 cat main.c 看一下咱们目前所于目录下的 main.c 文件。

opebet体育app 13

image.png

顾,在斯 main.c 的公文中,我们的 main 函数获取了命令执行参数的个数
argc(整数型)和同一多级参数(字符指针的指针,可以就此拜访数组的花样拜访)。

其一顺序将预期输出命令执行参数的多寡,并且用各一个参数逐一列出。
对接下去让我们 make 一下,完成对是顺序的编译。

opebet体育app 14

image.png

完成了 make,就为我们拿它们运行起来吧。请输入 ./main
并运行起来是次,并当事后自由输上有些空格分隔开之字符串,例如:

./main I feel better after this

我们先后中之argc
接受到的参数一共是几个,它们分别对应了我们在巅峰中输入的啦有之情节呢。

opebet体育app 15

image.png

 

文件操作

前面课程中,我们学习、设计的装有程序还是自从正式输入进行读取、向专业输出进行勾勒来底,操作系统也咱准备好了正式输入、标准输出的界面。在及时节课中,我们即将学习如何由文本被进行读取、如何向文件进行写入。

以朗诵文件之时段咱们得事先来一个好叫咱走访到文件之 文件指针(file
pointer),它是一个FILE色的指针。

俺们好透过下面的方式宣示一个文本指针。

FILE *fp;

这会儿,如果我们期望对一个文书进行操作,我们得事先采取

fp = fopen(文件路径, 访问模式);

用文件指针和文件涉及起来,其中第一个参数是一个字符串,对许了我们希望访的文书路径。第二只参数是看模式,它可以是意味着仅念模式之"r",也足以是表示无非写模式之"w",还得是当文件末尾追加的"a"

当我们以文件指针和文件涉及起来后,我们就算足以经过fgetc(fp);获得当前指针之后位置的一个字符了,每获得一个字符,指针会向后倒一个字符(如果到文件尾则会回来EOF)。

咱们这通过fputc('c', fp);的方将字符'c'写入到fp事关的文书内了。

询问及这些信后,我们尽管足以兑现以一个文件复制到另外一个文书内之函数了,例如:

void filecopy(FILE *in_fp, FILE *out_fp) {
    char ch;
    while ((ch = fgetc(in_fp)) != EOF) {
        fputc(ch, out_fp);
    }
}

这函数接收的有限单参数都是文本指针。这个函数会通过一个只是读模式的文本指针逐字符地读取,并且经过一个不过写模式的文件指针逐字符地将有着字符写起,从而从至复制文件内容的意。

您需要留意,在吃文件指针进行命名的时,要规避 stdin、stdout 和 stderr
这三个号。因为就三单名称其实就用于规范输入、标准输出、标准错误的文本指针。

君或许会见咨询了,那我们看的 stdinstdout
stderr的就三独文本指针可以直接采用与否?回答是必然之。

咱是经过
fgetc(stdin);得到来自专业输入的字符,也足以透过fputc(ch, stdout);
fputc(ch, stderr);将变量 ch面临之字符输出到正规输出或正规错误中之。

除fgetc和fputc之外,我们还可以fscanf和fprintf函数。这点儿只函数都十分像咱已特别熟悉的scanf和printf函数,只是不过,scanf和printf
可以于作 fscanf和fprintf 的特例。

俺们下 fscanf 从文本指针in_fp进行读取时,可以形容成:

fscanf(in_fp, "%c", &a);

设若如果我们形容

fscanf(stdin, "%c", &a);

当即将完全与下部直接采用 scanf 的法等。

scanf("%c", &a);

恍如地,我们运用fprintf向文件指针out_fp进行勾勒来时,可以形容成:

fprintf(out_fp, "%c", a);

要是使我们刻画

fprintf(stdout, "%c", a);

旋即将完全与下部直接下 printf的方法相当。

printf("%c", a);

于应用文件同时规定不再继续利用后,我们设透过下面所显示之主意拿文件指针fp与公事之涉嫌断开。你可用其就是与fopen相反的一个操作。

fclose(fp);

苟您免在先后中使fclose,程序正常化了时,程序会为有打开的文本调用fclose

stdinstdout其实呢是为辟的文书指针,如果您以为之所以非交的言辞,其实也是可以采用fclose以他们关闭掉的。你可好试一跃跃欲试,关闭
stdinstdout 会对咱先写了之程序带来什么的震慑吗?

4.将编译data_.c编译为目标文件data_.o

gcc -c -o data_.o data_.c -IC:/mono-3.2.3/include/mono-2.0

 

5.将data.o和data_.o 合成为一个十足的静态库:data.a

ar rcs data.a data_.o data.o

 

6.编译test.c和连接data.a,生成 test.exe

gcc -o output\test.exe test.c data.a %GCC_OPT% -lmonosgen-2.0

 

最后之战果如下

opebet体育app 16

 

winform 最中心的 lib 有以下几只,添加到lib\mono\gac目录下。

opebet体育app 17

 

运作试试,没有问题

opebet体育app 18

 

那么最关注的事情来了。

此文件从包了mono的.net 运行时,size有差不多格外也?

opebet体育app 19

 

减一下

opebet体育app 20

 

对待传统的打包.net 运行时 这当是一个不胜令人满意的品尝吧,结束!

 

opebet体育app 21

编译后的先后:opebet体育app 22

 

 

一经大家觉得有得,下篇文章我会写什么的布局 打包环境。

标签:, , , ,

Your Comments

近期评论

    功能


    网站地图xml地图