-
1 软硬件配置 类别子项版本 硬件CPU鲲鹏920网络1822网卡存储SATA 4T内存--OSCentOS7.6Kernel4.14.0-115.el7a.0.1.aarch64软件Speccpu2006gcc7.3.02 组网配置不涉及 3 问题3.1 问题描述:编译升级gcc到7.3.0后连跑speccpu2006报错libstdc++.so.6: cannot open shared object file: No such file or directory3.2 问题分析:我们编译的gcc7.3.0的lib64下是有libstdc++.so.6的库的,但是speccpu却打印不存在,可能是环境变量设置问题我们在/etc/profile中添加如下内容(LD_LIBRARY_PATH环境变量主要用于指定查找共享库(动态链接库)时除了默认路径之外的其他路径。(该路径在默认路径之前查找))export LD_LIBRARY_PATH=/usr/local/gcc-7.3.0/lib64:$LD_LIBRARY_PATHsource /etc/profile然后重新执行测试可以成功3.3 问题结论:编译的gcc7.3.0下的动态库speccpu2006无法找到,需要通过LD_LIBRARY_PATH环境变量添加gcc7.3.0下的动态库路径,在/etc/profile中添加export LD_LIBRARY_PATH=/usr/local/gcc-7.3.0/lib64:$LD_LIBRARY_PATH解决
-
如何实现从x86到鲲鹏平台90%C/C++代码自动迁移(华为 张汝涛)直播简介:C语言自诞生以来,被广泛用与开发各行各业的软件。C++语言既保留了C语言有效性、灵活性等特点,又增加了面对对象编程的支持,具有强大的编程功能。C/C++语言多年来移植是程序喜爱的编程语言之一。C/C++是编译型语言,硬件平台的切换将导致原有C/C++程序不能运行,开发者不得不解决软件移植问题。软件移植是个“脏活”,需要开发者修改源码、编译、再修改、再编译,费时费力。 直播亮点:怎样才能帮助开发者在鲲鹏平台上快速移植C/C++软件并完成编译呢?怎样才能帮助开发者在鲲鹏平台上快速运行C/C++程序呢?怎样才能帮助开发者快速定位软件的性能瓶颈并优化呢?怎样才能实现90%C/C++代码快速迁移到鲲鹏平台呢? 预习材料:https://bbs.huaweicloud.com/forum/thread-34057-1-1.html,华为鲲鹏开发套件提高C/C++软件迁移效率,实现90%C/C++代码自动迁移到鲲鹏平台。回放链接:https://hdcwebinars.huaweicloud.com/watch/rm2kr1xm 专家简介:华为智能计算部门主任工程师,华为鲲鹏开发套件的设计者。从事软件开发20年,聚焦于开源软件开发、移植和性能优化,完善Arm64软件生态。
-
1 问题背景项目中遇到鲲鹏芯片架构下编译C/C++代码编译时间过长,增加了业务版本CI时间,需要优化。本案例分享一下基于cmake和GCC编译优化的思路和措施。2 原因分析获取环境以后,利用开源软件A编译测试,逐步对可能影响编译时间的因素排查调优分析。1. 充分发挥多CPU并行处理功能Make阶段利用多线程处理,将进程个数设置成cpu的核数,提高编译速度。效果:相对于单线程编译来说,有几倍提升。2. 降低iowait同过iostat观察,编译过程中有部分时间出现iowait,特别是编译写文件的时候。方法:修改缓存VM参数,增加缓冲:以下参数和X86配置不一致,修改一致为:(1)/proc/sys/vm/dirty_ratio 修改前10,修改后20效果: 整体编译时间减少2s左右,说明有一定的效果,还不是关键因素。3. 去掉nohz=off/proc/cmdline如果存在nohz=off配置,会对系统性能有影响,尝试去掉测试性能方法:找到系统中/boot/efi/EFI/XXX/grub.cfg的nohz=off去掉,并重启服务器效果:去掉nohz=off参数后测试性能和修改前差不多4. Gcc参数加入ARM相关编译参数新版本gcc里面加入了对ARM架构的编译优化参数,如-mtune=tsv110,-march=armv8-a,尝试是否对编译性能有提升。方法:升级编译gcc到9.2.0版本,在编译脚本gcc后面加上-mtune=tsv110,-march=armv8-a参数,重新对程序进行编译测试性能。效果:添加参数后gcc编译性能无提升,平均执行时间和修改前差不多。此选项加入是优化编译软件运行性能的,不会降低编译时间。5. 内存页大小通过perf分析,编译代码有很多跳转指令,汇编代码中加载内存指令的执行时间段很高,分析可能是内存主要瓶颈。Perf热点函数分析内存换页函数调用频繁,浪费时间。可以通过扩大内存页来加大每页命中率,减少页切换的资源浪费。方法:获取内核源码,修改.config文件参数CONFIG_ARM64_64K_PAGES=y(注意,执行make menuconfig通过界面修改更为全面),重新编译内核,然后系统用新内核启动。检查是否修改成功: getconf PAGESIZE 显示为65536 即表示修改成功。效果:编译时间缩短20%左右,优化效果较大。3 解决方案综上分析,通过并发编译、修改vm缓存参数和调整内存页大小为64K对编译时间优化有显著效果。修改方法也在上文有描述。4 总结优化编译时间在版本构建的时候很关键,能节约不少构建时间,提高生产效率。目前大多是对编译出程序性能的优化,这样必然会增加编译时间,比如说如果用高版本的GCC编译器,编译出来的程序性能会更好,但是编译时间可能变长了,相比低版本的GCC来说。也就是说,如果想优化编译时间,尽量避免去用新GCC版本,或者利用新的GCC编译优化参数。 提供程序运行性能,让他跑得更快,还是老一套,去分析程序运行时的系统瓶颈,解除瓶颈后会对性能有提升,如本案例中内存就是一个瓶颈。
-
1、简介Boost是为C++语言标准库提供扩展的一些C++程序库的总称。Boost库是一个可移植、提供源代码的C++库,作为标准库的后备,是C++标准化进程的开发引擎之一,是为C++语言标准库提供扩展的一些C++程序库的总称。2、基础环境类别子项版本获取地址(方法)华为云虚拟机KC1(920)--OSCentOS7.6Kernel4.14软件包 boost1.69.0https://kojipkgs.fedoraproject.org//packages/boost/1.69.0/13.fc32/src/boost-1.69.0-13.fc32.src.rpm3、依赖安装yum install -y mock gperftools-devel libpcap-devel libstemmer-devel openssl-devel pcre-devel python3-scons snappy-devel yaml-cpp-devel zlib-devel valgrind-devel libcurl-devel python3-devel 4、组件编译安装 下载并解压组件wget https://kojipkgs.fedoraproject.org//packages/boost/1.69.0/13.fc32/src/boost-1.69.0-13.fc32.src.rpm#boost-devel安装编译rpm -ivh boost-1.69.0-13.fc32.src.rpm#编译rpmbuild -ba /root/rpmbuild/SPECS/boost.spec 安装依赖yum install -y gcc-c++ bzip2-devel python3-numpy libicu-devel openmpi-devel mpich-devel 修改boost.spec中关于python3-numpy的部分,python3-numpy编译出来的就是python36-numpyyum install –y python36-numpy修改boost.spec中关于gcc-c++的部分,去掉gcc-gcc安装部署参考:《华为云鲲鹏云服务最佳实践-gcc-7.3.0安装部署指导》https://bbs.huaweicloud.com/forum/thread-39010-1-1.html5、系统配置无6、测试无7、参考信息无8、FAQ8.1问题:boost编译报错./boost/python/detail/wrap_python.hpp:50:11: fatal error: pyconfig.h: No such file or directory 解决方法:yum install -y python-devel8.2问题:boost编译报错ERROR: No build ID note found in /root/rpmbuild/BUILDROOT/boost-1.69.0-13.el7.aarch64/usr/bin/quickbook 解决方法::是在spec文件中任意位置添加如下参数:%define __debug_install_post %{_rpmconfigdir}/find-debuginfo.sh %{?_find_debuginfo_opts} "%{_builddir}/%{?buildsubdir}" %{nil}8.3问题:boost编译报错error: File not found: /root/rpmbuild/BUILDROOT/boost-1.69.0-13.el7.aarch64/usr/lib64/libboost_stacktrace_addr2line.so.1.69.0解决方法:注释掉spec文件中%{_libdir}/libboost_stacktrace_addr2line.so.%{sonamever} 8.4问题:boost编译报错证书未生成解决方法:将开始报错的所有证书都注释 8.5问题:boost编译报错error: Installed (but unpackaged) file(s) found: 解决方法:找到/usr/lib/rpm/macros 文件中%__check_files %{_rpmconfigdir}/check-files %{buildroot} 注释掉
-
1、简介Boost是为C++语言标准库提供扩展的一些C++程序库的总称。Boost库是一个可移植、提供源代码的C++库,作为标准库的后备,是C++标准化进程的开发引擎之一,是为C++语言标准库提供扩展的一些C++程序库的总称。2、基础环境类别子项版本获取地址(方法)华为云虚拟机KC1(920)--OSCentOS7.6Kernel4.14软件包boost1.55.0 https://kent.dl.sourceforge.net/project/boost/boost/1.55.0/boost_1_55_0.tar.gz 3、依赖安装无4、组件编译安装下载安装包(指定路径)cd /opt/wget -c https://kent.dl.sourceforge.net/project/boost/boost/1.55.0/boost_1_55_0.tar.gz --no-check-certificatetar -xzvf boost_1_55_0.tar.gz./bootstrap.sh --with-libraries=system,filesystem,log,thread --with-toolset=gcc./b2 toolset=gcc cxxflags="-std=c++11" ./b2 install 运行./b2 install 命令,默认安装在/usr/local/lib目录下头文件在/usr/local/include/boost目录下install 后面可以加参数--prefix=path 5、系统配置无6、测试无7、参考信息无8、FAQ无
-
C++实践教学精品课标准课程地址课程概述:本课程适合作为高等学校计算机专业及相关专业C++语言程序设计课程的教材,可供从事计算机软件开发人员参考使用。本课程主要介绍了C++语言编程相关知识,重点介绍C++语言概述、函数、类与对象、数据共享与保护、数组、指针、字符串、继承、派生、多态、群体类和群体数据的组织、泛型、C++标准模板库、流类库、输入输出及异常处理。 通过本课程,学生能够学习并了解C++语言语法,体会和领悟面向对象程序设计方法和泛型程序设计方法的优势,结合课程中的编程练习题,能够进一步加深学生动手能力,提升学生对C++知识的掌握和实际应用。材料数作业数习题数五星推荐搭配1591288《C++习题库》含376道习题 作者介绍华为云教育,本课程由华为云教育内容开发团队开发完成,团队主要负责教育解决方案内容开发和建设。包括但不限于课件、视频、习题、代码、案例项目、实训课等。 课程定位:本课程根据人才培养目标,制定涵盖低级,中级,高级等多级分类的知识点、原理、定理等课程体系,满足人才培养需求,包括知识要求、能力要求、素质要求。C++语言为C语言的进阶,学习它是很有必要的,做人工智能的研究,想要深入底层,TensorFlow的核心是用C++写的;做游戏开发,包括端游和网游后台,以发挥计算机的全部性能,需要C++;做智能硬件、嵌入式或硬件驱动开发,C++会提供更多工具,生产效率更高。 岗位及从业方向:岗位:游戏开发工程师、服务器开发工程师、应用开发工程师、C++逆向开发工程师、嵌入式开发工程师、图像处理工程师。从业方向:服务器端开发、游戏开发、虚拟现实仿真、数字图像处理、网络安全、黑客攻防、破解等方向。 前/后导课程:C++语言程序设计可以说是C语言程序设计的进阶课程,学好《计算机应用基础》、《C语言程序设计》,会让你学习起来简单得多。《计算机应用基础》——>《C语言程序设计》——>《C++程序设计》、《Java程序设计》、《数据结构》 本课程的主要任务是:1. 掌握面向对象程序设计的各种概念、机制及其用法2. 掌握C++泛型程序设计,熟练编写各类模板3. 熟练使用C++的标准模板库4. 初步具备用C++语言和面向对象的方法开发大型程序的能力5. 通过学习本课程,让学习本课程的人有一个扎实的计算机基础,对计算机架构,操作系统,编程语言,计算机网络有一个本质的认识,做到以不变应万变,并且可以独立开发模仿一些常用的软件工具和网站以及安卓程序,解决日常生活中遇到的各种计算机问题。6. 考核达标后,基本达到入职企业所需具备的软件开发职业素质。7. 培养学生严肃,认真一丝不苟的工作作风。培养学生积极思考,通过算法编程题,锻炼思维能力,培养创新能力。8. 为以后深入其他任何计算机领域奠定坚实的根基,未来才能够走的更远,站的更高,解决一般程序员无法解决的问题,成为优秀的人才。 本课程知识教学目标:1.了解计算机程序设计语言的基本知识。2.掌握基本类型、表达式、数据的输入输出、算法的基本控制结构及枚举类型。3.掌握函数的定义、调用、参数传递、函数种类和使用。4.掌握类和对象的使用、构造函数、析构函数、UML类图、结构体、联合体。5.掌握数据共享、数据保护、多文件结构,了解编译预处理命令。6.掌握指针、数组的定义和使用。7.掌握类的继承与派生、派生类的构造定义和析构函数的使用。8.了解并掌握多态性的概述、运算符重载、虚函数和抽象类的使用。9.掌握函数模板与类模板的定义和使用及排序方法的分类使用。10.掌握泛型程序设计与C++标准模板库。11.了解流的概念及流类库结构、掌握输入输出流。12. 理解异常处理的思想,掌握C++异常处理的实现。 教学大纲:第1章绪论1) 计算机程序设计的发展2) 面向对象的方法3) 面向对象的软件开发4) 信息的表示和存储5) 程序的开发过程通过本章节的学习,学生可以:1) 了解 计算机程序设计语言的发展、计算机语言的分类2) 掌握信息的分类、几种进位计数制的转换3) 理解源码、反码、补码的定义及使用4) 掌握定点数、浮点数、数的表示范围及非数值信息的表示5) 了解程序开发的过程 第2章C++简单程序设计1) C++语言概述2) 基本数据类型和表达式3) 数据的输入与输出4) 算法的基本控制结构5) 枚举类型通过本章节的学习,学生可以:1) 了解 C++ 语言发展和应用2) 掌握 C++能够处理的基本数据类型和表达式3) 了解IO流、简单IO格式控制。4) 理解并掌握算法的基本控制结构及使用方法,包括if、switch、while、do-while、for、break、continue、goto语句5) 掌握枚举类型的定义和使用 第3章函数1) 函数的定义与使用2) 内联函数3) 带默认参数值的函数4) 函数重载5) 使用C++系统函数通过本章节的学习,学生可以:1) 学会函数的定义及使用2) 理解函数调用的形式、掌握嵌套调用和递归调用3) 掌握函数参数传递的定义及使用方法4) 理解并掌握内联函数的使用、注意事项及内联函数的应用5) 掌握带默认参数值的函数的使用6) 学会函数重载如何使用及注意事项7) 了解C++系统函数8) 学会将一段功能相对独立的程序写成一个函数第4章类与对象1) 面向对象程序设计的基本特点2) 类和对象3) 构造函数和析构函数4) 类的组合5) UML图形标识6) 结构体7) 联合体通过本章节的学习,学生可以:1) 了解面向对象的基本概念2) 掌握类和对象的声明使用3) 掌握构造函数及析构函数定义和使用4) 理解类的组合、会使用向前引用声明5) 了解UML类图6) 掌握结构体的定义和初始化7) 学会联合体的声明、内存分配及使用方法 第5章数据的共享与保护1) 标识符的作用域与可见性2) 对象的生存期3) 类的静态成员4) 类的友元5) 共享数据的保护6) 多文件结构和编译预处理命令通过本部分的学习,使学生:1) 熟练掌握函数原型的作用域、局部作用域、类作用域、文件作用域2) 理解可用性的概念3) 了解什么是动态生存期和静态生存期,掌握变量的生存期与可见性4) 掌握静态数据成员的声明和使用5) 理解友元的定义,学会友元函数的使用6) 了解数据的共享、保护7) 掌握C++程序的一般组织结构8) 理解外部函数和外部变量的定义及使用方法9) 掌握标准C++库10) 学会编译预处理命令的使用 第6章数组、指针与字符串1) 数组2) 指针3) 动态内存分配4) 用vector创建数组对象5) 深拷贝与浅拷贝6) 字符串通过本部分的学习,使学生:1) 熟练掌握一维数组、二维数组、对象数组的概念、声明与使用2) 了解内存空间的访问方式3) 掌握指针的赋值及运算4) 理解动态内存分配及动态的使用5) 学会用Vector创建数组对象6) 理解深拷贝和浅拷贝的定义和使用7) 掌握用字符数组处理字符串的方法8) 熟练使用String类 第7章继承与派生1) 类的继承与派生2) 访问控制3) 类型兼容规则4) 派生类的构造、析构函数5) 派生类成员的标识与访问通过本部分的学习,使学生:1) 理解类的继承关系,学会使用继承关系实现代码的重用2) 了解继承与派生的概念、目的3) 理解派生类的声明及生成过程4) 掌握公有继承、私有继承、保护继承的定义及使用方法5) 了解类型转换的规则6) 掌握继承时及单一继承时构造函数的使用7) 了解作用域限定8) 掌握虚基类的引入、声明和作用9) 熟练掌握虚基类及其派生类构造函数的使用 第8章多态性1) 多态性概述2) 运算符重载3) 虚函数4) 抽象类通过本部分的学习,使学生:1) 理解多态的概念,学会运用多态机制2) 掌握多态的概念、类型及实现3) 学会重载“+”“-”运算符的使用4) 理解运算符重载的规则5) 掌握运算符重载为成员函数6) 掌握运算符重载为非成员函数7) 了解并掌握虚函数的概念和声明8) 了解为什么使用虚析构函数和使用方法9) 掌握纯虚函数的定义和使用10) 了解抽象类的作用和使用 第9章群体类和群体数据的组织1) 函数模板2) 类模板3) 线性群体4) 群体数据的组织通过本部分的学习,使学生:1) 理解函数模板的概念和定义方法2) 了解并掌握类模板的作用和声明以及使用3) 理解线性群体的概念4) 掌握动态数组类模板的使用5) 熟练掌握链表的基本操作:生成结点、**结点、查找结点、删除结点、遍历链表、清空链表6) 了解栈的概念,掌握栈的基本状态:栈空、栈满、一般状态7) 掌握什么是队列及队列的基本状态:队空、队满、一般状态8) 掌握循环队列的定义和使用 第10章泛型程序设计&C++标准模板库1) 泛型程序设计及STL的结构2) 迭代器3) 容器的基本功能与分类4) 顺序容器5) 关联容器6) 函数对象7) 算法通过本部分的学习,使学生:1) 了解泛型程序设计的基本概念2) 了解STL概念及组成3) 理解迭代器的分类、迭代器的区间4) 了解并掌握迭代器的辅助函数的使用5) 掌握输入流迭代器、输出流迭代器的使用6) 理解容器的基本功能和分类7) 了解顺序容器的接口和基本操作8) 了解三种顺序容器的特性9) 掌握顺序容器**迭代器的方法10) 学会以顺序容器为基础构建一些常用数据结构11) 了解优先级队列定义及使用12) 掌握关联容器分类和的基本功能13) 掌握函数对象的定义和使用14) 了解STL算法概念和分类15) 学会使用不可变序列算法、可变序列算法、排序和搜索算法、数值算法 第11章流类库与输入输出1) IO流的概念及流类库结构2) 输出流3) 输入流4) 输入/输出流通过本部分的学习,使学生:1) 了解IO流的概念及流类库结构2) 掌握输出流的分类及如何构造输出流对象3) 学会**运算符和操纵符的使用4) 掌握文件输出流成员函数的三种类型及使用5) 理解二进制输出文件6) 掌握字符串输出流的功能和应用7) 了解输入流的分类8) 掌握输入流对象的构造方法9) 学会使用提取运算符10) 理解输入流相关函数的使用方法11) 掌握字符串输入流功能和应用12) 理解并掌握输入/输出流两个重要的类 第12章异常处理1) 异常处理的基本思想2) C++异常处理的实现3) 异常处理中的构造与析构4) 标准程序库异常处理通过本部分的学习,使学生:1) 了解异常处理的基本思想2) 掌握异常处理的语法和异常接口声明3) 了解异常处理中的构造与析构4) 了解标准程序库异常处理方法5) 学会标准程序库的异常类的使用课时建议:序号课 程 内 容学 时 数合计理论教学实践教学实训教学教学实习1绪论222C++简单程序设计4223函数6424类与对象151235数据的共享与保护6426数组、指针与字符串6427继承与派生6428多态性5419群体类和群体数据的组织4410泛型程序设计&C++标准模板库54111流类库与输入输出2212异常处理321总计644816 教学过程与方法目标:建议在进行该课程的教学过程中,充分利用classroom平台的在线判题和授课能力,在讲完每个章节之后,通过在C++语言习题库中,根据该章节的知识点选择客观题(选择、判断、填空)等,进行选题出题,进行上课期间的随堂作业,在3~5分钟内,学生需要完成作业并提交,老师通过平台反馈的数据,及时了解学生对该章节知识点的掌握情况,对大部分学生都答错了的习题所对应的知识点,需要重点再讲解。 另外,可以通过C++语言习题库,根据知识点选择适量的在线编程题,作为作业下发给学生进行课后编程练习,通过学生提交的代码以及完成功能的正确率,对相关知识点进行重点讲解,通过课后编程题练习,也可以有效的提升学生的动手编程能力,这样就达到了不仅仅能掌握理论知识,还能动手将理论和实际相结合,提升学生的动手能力。在教学到第5章左右,可以结合classroom平台,给学生布置一些相对复杂的C++语言单人工程型习题,培养学生项目开发的能力,以及团队合作精神。 考核要求:(1)考核包括,期末考核70%,平时30%(2)理论考核采用闭卷形式,时间100分钟(3)题型为填空、选择、程序设计(4)考试内容分配:基础60%,综合40%(5)试卷难度分配:基本内容60%,适中内容30%,难度内容10%(6)技能考核方式是上机操作,主要考核程序改错和编程,通过classroom平台完成作业的提交,在线编程等。 参考文献:《C++语言程序设计》(第4版)郑莉 清华大学出版社
-
#百因必有果#怎么修改ARM服务器上大文件的内容?我先尝试了用python进行修改,但是使用普通的read write会消耗很长的时间,之后就在python中使用mmap,这个好像也没怎么改善,估计是语言的关系。最后通过网上查资料,找C或者c++,在c/c++中使用mmap,速度很快快,只要5s。实质是通过内存映射的方式,减少对io的使用,但是代价就是耗内存。希望对你们有帮助
-
#化为鲲鹏,我有话说#c#更看重的快速桌面应用,作为尝试替代VB和DELPHI的语言,继承了C/C++的基本语法,又进行了一系列的修改(因为c/c++有各自的ISO标准,推进标准并不那么容易,而c是构架于.net框架下的,他并不是navite的本地机器语言,编译后生成的也是中间代码
-
化鲲为鹏,我有话说 C++ 和 C 的设计哲学并不一样,两者取舍不同,所以不同的程序员和软件项目会有不同选择,难以一概而论。与 C++ 相比,C 具备编译速度快、容易学习、显式描述程序细节、较少更新标准(后两者也可同时视为缺点)等优点。在语言层面上,C++ 包含绝大部分 C 语言的功能(例外之一,C++没有C99的变长数组VLA),且提供 OOP 和 GP 的特性。但其实用 C 也可实现 OOP 思想,亦可利用宏去实现某程度的 GP,只不过 C++ 的语法能较简洁、自动地实现OOP/GP。C++ 的 RAII(resource acquisition is initialization,资源获取就是初始化)特性比较独特,C/C#/Java 没有相应功能。
-
#化鲲为鹏,我有话说#这次参加比赛的过程中遇到了,需要修改ARM服务器上大文件的内容的问题,一开始用python进行修改1g的文件,使用普通的read write消耗了很长的时间,大概60多s,后来找了方案,在python中使用mmap,这个好像也没怎么改善,估计是语言的关系。没办法,只能找C或者c++,在c/c++中使用mmap,好快,只要5s。原来他是通过内存映射的方式,减少对io的使用,代价就是耗内存。
-
解决方法:执行./configure时指定参数:./configure --host=arm-linux --build=arm-linux
-
我一直在思考这节课应该叫个什么名字。想来想去,觉得taste of java这个名字最好。随着编程经验的丰富,使用的编程语言也多起来。不同语言之间难免会进行对比。而语言的设计者在设计一门语言时,要面临很多问题,而且这些问题并没有完美的答案,而如何进行取舍很多时候真的就是一个理念,甚至是品味的问题了。Java是一门面向对象的语言不用进行深入地学习,只要是听说过Java的人,都知道Java是一门面向对象的语言。其实面向对象往宽泛了说,应该是一种编程思想,它是一种思维方式。而面向对象的编程语言则是指,编程语言提供了一种机制,使得我们可以用比较简洁的语法表达数据的抽象和封装。例如,PostgreSQL这个数据库就是用C编写的,但是它的源代码却很有趣,用struct 定义了很多结构体,然后用struct的嵌套模拟了类的继承(要知道,在C++中,struct甚至都可以和class换用),而对象的布局在结构体里也显得更加清晰。这也是一种面向对象的编程方式,但我们却不认为C是一种面向对象的编程语言,这是因为C并不提供方便的语法让我们轻松地使用面向对象编程。而C++, Java, Python这些语言则提供了class关键字来进行类的定义,我们会说这些语言是面向对象的。我们知道,C++里是可以定义全局变量,全局函数的。很多脚本语言,虽然是面向对象,但仍然可以在类定义之外声明变量,定义函数,执行操作。举个最简单的例子,我们看几种语言的hello world// C++的写法 int main() { cout << "hello world" << endl; return 0; } # Python 的写法 print "hello world" // Scala的写法 println("hello world") /* Java 的写法 */ public class Main { public static void main(String args[]) { System.out.println("hello world"); } }很明显,Java最啰嗦,C++次之,python和scala就都比较简洁。从这个简单的例子就能看出来语言的不同品味。python和scala倾向于灵活,一个具体的操作可以脱离函数实体而直接运行。C++就会严谨一些,所有的动作都必须被封装到函数中去,然后通过执行一个函数来做一些事情(比如往控制台打印字符)。而Java的要求就更严格了,Java要求语言中,所有的函数都必须定义在一个类里,函数不能脱离类而存在。这样的规定使得Java显得死板,但有时候太过灵活,反而很难掌握。比如scala,内部分裂为两个流派,一派把scala做为Java的改进,另一派完全使用函数式编程,而不主张对Java进行改进。对于初学者,在还没掌握一门语言的全貌之前,就听各种“专家”,“大牛”大谈编程范式,相互鄙视,然后听了一堆似是而非的概念,其实是有害的。但是Java不同,语法的死板意味着更少的歧义。强对象使得Java成为了学习面向对象编程的最佳入门语言。面向对象的不足凡是有利必有弊,强对象编程,使得语法简单统一,但也有其缺点,而且有很多。我们在接下来的课程里会一点点接触到。我们今天先看第一个。有些变量和函数确实没必要定义在一个类里。强行规定这些函数在类里,反而显得累赘。想一个例子,比如正弦函数sin,常数PI,这些函数或者常量值为什么要定义在类里呢?一定要定义的话,定义在哪个类里合适呢?Java的做法是把数学函数封装到一个叫做Math的类里。叹气...一个叫Math的类,太不直观了。再来思考一个问题,如果说,我们这样写class Math { public double sin(double x) {/*code goes here*/} }那么,我每次要调用sin函数都得写成new Math().sin(x)因为,我们只能通过Math类型的对象去调用定义在Math类中的函数。这太不科学了。为了调用一个本来可以全局存在的函数,我们却要新建一个对象?!语言的设计者肯定也不会这么傻。于是,他们引入了static这个关键字。Static关键字当我们把一个函数或者变量加上static限制以后,就可以在不创建一个对象的情况下,直接使用类里的函数或者变量了。class Math { public static double sin(double x) {/*code goes here*/} } Math.sin(x)编程语言的关键字是有它内在的逻辑的,不要去死记硬背,通过上面的分析,我们就能知道static关键字用于修饰变量和函数是不得不这样做,而不是大家闲得慌,去加这么一个关键字故意去难为新手们。好了,有了static关键字,世界好像变得合理了一点。但是做为语言设计者,还是不满意,如果我有一个程序,里面会用到大量的数学函数,然后我就看到了满屏幕的Math.xxxhttp://MatM。要是能把这个Math去掉就好了。然后设计者们就把主意打到了import那里。我们能不能把这些本来就是全局函数,全局常量的值导入到当前文件中,好像他们本身就没有被封装到类里一样?于是这种语法就出现了:import static java.lang.Math.*; public class Main { public static void main(String args[]) { System.out.println(sin(PI / 2)); } }好了,通过这种方法,就把Math中的所有static方法和常量都引入到当前文件了,我们再也不用使用Math开头去引用一个静态函数了。其实static的语义到这一步就基本说清楚了。如果我是Java的设计者,我不会再为static增加其他用法了。但是不幸的是,Java有一个坏品味,那就是重用关键字。这让一些本来简单的事情又变复杂了。static关键字还可以用来定义静态代码块。static块可以置于类中的任何地方,类中可以有多个static块。在类初次被加载的时候,会按照static块的顺序来执行每个static块,并且只会执行一次。这种与类加载有关的逻辑,显然应该甩锅给ClassLoader。比如 ClassLoader在加载一个类的时候,调用类中的static onLoad()方法,也比静态代码块这种引起混淆的语法好。这样的设计才会显得清晰。静态代码块是什么鬼!?这显然是一个关键字复用的错误例子。我们没办法改变这种设计,只能去适应。记住这个用法吧。static 函数里不能使用this, super?废话!你只要明白了static 函数其实是全局函数,它只是因为Java的强对象的要求,而不得不找个类“挂靠”,它本身与任何类都没有关系。所以在static 方法里,当然不能直接访问某一个类的成员变量和成员函数了。但是呢,一个类让一个static函数挂靠了,总得有点好处吧?要说好处,倒也有一个,那就是类的成员函数调用static方法不用带类名了。class Example { public static void sayHello() { System.out.println("Hello, everybody~"); // 这个当然不能用。static函数与其挂靠的那个类的对象没有任何关系。 // static函数是全局唯一的。 // this.sayBye(); } public void sayBye() { System.out.println("Good Bye~"); } public void saySomething() { // 唯一的一点好处,大概就是成员函数里这样三种写法都是OK的。 // 但这个没卵用。我更喜欢Java只保留第三种写法,免得大家误会。 this.sayHello(); sayHello(); Example.sayHello(); this.sayBye(); } }final关键字final 用于修饰一个类,那么这个类就不能再被其他类继承。用于修饰一个方法,这个方法不能被覆写。这是非常好的一个东西。可以避免我们造出混乱的继承结构。比如Java中的String类就是final的,它是不能被继承的。// 想创建一个自己的String类是不行的。因为String是final的。class MyString extends String {}再看修饰method的情况:class A { public final void f() { } // 这里是OK的,只是一次重载 public final void f(int a) { } } class B extends A { // 会报错,说f是final的,不能覆写 public void f() { } }好。到此为止,final是如此地清晰。但不幸的是,Java的设计者不知道是出于什么考虑,把final也拿来定义变量。这就让人无语了。这是const关键字做的事情啊。重用关键字决不会让语法变得更简洁。对于一个final变量,如果是基本数据类型的变量,则其数值一旦在初始化之后便不能更改;如果是引用类型的变量,则在对其初始化之后便不能再让其指向另一个对象。而且,事实证明,Java的final和C++的const还真就是同样的。就连一些容易混淆的地方都原封不动地迁移过来。我们挨着看。先看基本用法。final int a = 1; a += 2; // 会报错,我们不能修改一个final变量再看一下容易引起混乱的地方。public class Hello { public static void main(String args[]) { String a = "go die, "; final String b = "final"; String c = "go die, " + b; String d = a + b; String e = "go die, final"; System.out.println(e == c); //true,比较两个变量是否指向同一个对象 System.out.println(e == d); //false System.out.println(c.equals(d));//true,比较两个字符串的值是否相同 } }结果可能出乎你的意料。我来解释一下。在编译阶段,变量c其实已经是"go die, final"了,等到我们后面分析Java字节码文件的时候就会看到,c和e是指向了常量池中的同一个字符串,也就是“go die, final"。所以它们其实是同一个对象。但是d却是运行时生成的,并不引用常量池中的"go die, final"这个字符串,所以,e和d并不是同一个对象,虽然它们的值相同。这和C++中编译时const变量转成编译时常量如出一辙。究其根本原因,还是在于b 在编译阶段就已经被当作常量“final” 去做下面的编译了。final关键字被用来当做const用,实在不是个好的品味。当然,const这个关键字是保留字,就是说在Java中虽然现在没用,但不保证以后不会用。你是不能拿这个词来当变量名的。额外加一句,如果一个变量在整个执行阶段不会被修改,那么加上final进行修饰是一个好的编程习惯。好了。我们今天通过static 和 final 这两个关键字来初步了解了一下Java的设计品味。语言的设计品味是一个很大的话题。我们会就这个话题继续我们的课程。
-
如图所示,这个文件有何作用,变红有影响吗哪位大神给解答下
-
【星云测试最新发布】 —Wings c/c++测试驱动自动生成工具软件 星云测试在华为云市场最新发布了,Wings c/c++测试驱动自动生成工具软件。Wings是一款用于单元测试测试用例驱动框架自动生成工具,这款工具主要是全自动生成单元测试驱动代码与测试数据。解决了做单元测试耗时耗力,编写难度大等问题。大幅提升了开发和测试效率,为企业在单元测试环节,节省至少一半的人工和时间成本。 产品特点:(1) 程序参数深度分析问题Wings通过编译器底层技术,将输入的源文件,按照函数为单位,形成模块对象。对象中包含函数的输入参数,返回值类型等信息,供驱动函数模块和测试用例模块使用。每个文件作为一个单元,针对其中的每个函数的每个参数进行深度解析,对于嵌套类型,复杂类型等都可以实现精确的解析和分解,将复杂类型逐层讲解为基础数据类型,并产生参数结构的描述文件(PSD)。(2) 函数驱动自动生成模块依据PSD文件的格式信息,自动生成被测源程序的所有驱动函数,单元测试过程不再依赖开发人员手动编写测试函数,只需将生成的驱动函数和被测源文件一起编译,即可执行测试并查看测试结果。测试驱动自动生成程序基于PSD描述,全自动构建驱动被测程序运行的所有参数,必须的全局变量,并可根据复杂变量的层级结构产生结构化的测试驱动程序,可以节省大量的单元测试用例的编写时间。(3) 测试数据自动生成与管理 用于自动生成测试数据,测试数据与被测函数提取的信息相互对应,数据以一定的层次逻辑关系存储在json文件中。数据和经过分解和展开后的数据类型是一一对应的。这些数据用户可以根据业务要求随意边际,并且用json文件进行结构化,层次化展示,非常的清晰。其中的测试数据包括全局变量值、被测函数调用时的参数值。 突出优点:1. 可以为任意复杂参数结构C语言开发的系统全自动生成测试驱动程序2. 可完成对于被测试函数的参数进行多层编译解析,并完成复杂参数赋值的代码的自动生成。3. 支持被测函数引用的全局变量的分析和自动赋值程序的生成。4. 能够区分系统变量和用户变量,对于复杂的系统变量可由用户自定义赋值模板。例如File类型,而不是把复杂的系统变量全部展开。5. 支持多层次的可视化的数据表格来对变量进行赋值,而无需关注驱动程序本身。数据表格可以表达任意深度和多层次的数据关系,用户只需要对表格数据进行编辑,自动生成的驱动程序会自动完成表格数据的读取和参数赋值的构造过程。6. Wings支持所有C语言的数据类型(基础类型,结构体,指针,数组,枚举等)以及高层级数据结构。例如链表的分析和对应的驱动和数据表格框架的生成。7. Wings生成的代码与人工写的非常相近,可读性强,自带注释和按照层次的缩进和代·码编排。 对Wings有兴趣的用户可以通过(http://www.teststars.cc)与星云测试团队取得联系,抢先体验wings的强大功能,同事星云测试旗下多款测试工具也为大家开放免费体验在网即可立即使用。
上滑加载中
推荐直播
-
华为云码道Agent集成与鸿蒙实战2026/08/11 周二 19:00-21:00
王一男-华为云码道产品规划专家;李炎-华为云码道产品专家;彭江敏-华为云鸿蒙端云一体化开发专家
本次直播带你解读华为云码道7月份产品新特性、新功能。更有专家演示码道Agent Space × 钉钉机器集成实战,从0到1打通消息通道;码道鸿蒙端云一体化实战,快速搭建员工签到系统。
回顾中 -
华为云开发者AI素养直播课·第五期2026/09/04 周五 16:00-18:00
林华鼎-华为云AI开发者运营负责人;蒋春阳-华为云AI开发者案例开发专家
本期直播内容: AI工具体验营 · 第5-8课连讲。Agent-Team 多智能体协作完成毕业设计实践
回顾中 -
华为云开发者AI素养ClassRoom·第六期2026/09/08 周二 19:00-20:00
樊渊-2026华为软件挑战赛冠军
高手来了:看软挑高手解析二维排样问题—从工业难题到算法突破
回顾中
热门标签