当前位置: 首页 > 编程日记 > 正文

20145231 《信息安全系统设计基础》第11周学习总结

20145231《信息安全系统设计基础》第11周学习总结

教材学习内容总结

异常

异常是异常控制流的一种形式,由硬件和操作系统实现。简单来说,就是控制流中的突变。
出现异常的处理方式:


1.处理器检测到有异常发生
2.通过异常表,进行间接过程调用,到达异常处理程序
3.完成处理后:①返回给当前指令②返回给下一条指令③终止
1、异常处理

异常号:系统为每种类型的异常分配的唯一的非负整数。

异常表:系统启动时操作系统就会初始化一张条转变,使得条目k包含异常k的处理程序的地址。

异常号是到异常表中的索引,异常表的起始地址放在异常表基址寄存器。

异常类似于过程调用,区别在:


1.处理器压入栈的返回地址,是当前指令地址或者下一条指令地址。
2.处理器也把一些额外的处理器状态压到栈里
3.如果控制一个用户程序到内核,所有项目都压到内核栈里。
4.异常处理程序运行在内核模式下,对所有的系统资源都有完全的访问权限。
2、异常的类别

故障指令:执行当前指令导致异常(陷阱、故障、终止)

中断处理程序:硬件中断的异常处理程序(中断)

异常的类别如下图。异步异常时有处理器外部的I/O设备中的事件产生的,同步异常时执行一条指令的直接产物

888584-20161127183759034-1315956499.png

陷阱是有意的异常,是执行一条指令的结果,最重要的用途——系统调用

故障是由错误状况引起,可能能够被故障处理程序修正。结果要么重新执行指令(就是返回当前指令地址),要么终止。典型示例:缺页异常

3、Linux/IA32系统中的异常

IA32系统中的异常列表如下

888584-20161127183820456-1204513054.png

每一个系统调用都有一个唯一的整数号,对应于一个到内核中跳转表的偏移量

888584-20161127183843284-299655717.png

在IA32中,系统调用通过一条陷阱指令提供:

int n;//n为异常号
所有的到Linux系统调用的参数都是通过寄存器传递的。惯例如下:

%eax:包含系统调用号

%ebx,%ecx,%edx,%esi,%edi,%ebp:包含最多六个任意参数

%esp:栈指针,不能使用

进程

进程的经典定义:一个执行中的程序的实例。

系统中的每个程序都是运行在某个进程的上下文中的。

上下文:由程序正确运行所需的状态组成的。

进程提供给应用程序的关键抽象:

一个独立的逻辑控制流:独占的使用处理器

一个私有的地址空间:独占的使用存储器系统

1、逻辑控制流

一系列的程序计数器PC的值,分别唯一的对应于包含子啊程序的可执行目标文件中的指令,或者是包含在运行时动态链接到程序的共享对象中的指令,这个PC值的序列就叫做逻辑控制流。

进程是轮流使用处理器的。每个进程执行它的流的一部分,然后被抢占,然后轮到其他进程。但是进程可以向每个程序提供一种假象,好像它在独占的使用处理器。

逻辑流示例:异常处理程序、进程、信号处理程序、线程、Java进程

2、并发流

一个逻辑流的执行在时间上与另一个流重叠。(与是否在同一处理器无关)

两个流并发的运行在不同的处理机核或者计算机上。

并行流并行的运行,并行的执行。

3、私有地址空间

进程为程序提供的假象,好像它独占的使用系统地址空间。一般而言,和这个空间中某个地址相关联的那个存储器字节是不能被其他进程读写的。

4、用户模式和内核模式

用户模式和内核模式的区别就在于用户的权限上,权限指的是对系统资源使用的权限。

具体的区别是有无模式位,有的话就是内核模式,可以执行指令集中的所有指令,访问系统中任何存储器位置;没有就是用户模式。

进程从用户模式变为内核模式的唯一方法是通过异常——中断,故障,或者陷入系统调用。

Linux的聪明机制——/proc文件系统,将许多内核数据结构的内容输出为一个用户程序可以读的文本文件的层次结构。

888584-20161127214120956-411005762.png

5、上下文切换

操作系统内核使用上下文切换这种较高层形式的异常控制流来实现多任务。上下文切换机制建立在较底层异常机制之上。

上下文:内核重新启动一个被抢占的进程所需的状态。由一些对象的值组成:

•通用目的寄存器

•浮点寄存器

•程序计数器

•用户栈

•状态寄存器

•内核栈

•内核数据结构:页表、进程表、文件表

上下文切换机制:


1.保存当前进程的上下文2.恢复某个先前被抢占的进程被保存的上下文3.将控制传递给这个新恢复的进程。
可能发生上下文切换的原因:•内核代表用户执行系统调用时•中断

系统调用错误处理

系统会使用错误处理包装函数,系统级函数是小写,他们的包装函数名大写,包装函数调用基本函数,有任何问题就终止,如果没有问题和基本函数是一样的。

进程控制

1、获取进程ID

每个进程都有一个唯一的正数进程ID(PID)。


#include <sys/types.h>
#include <unistd.h>

pid_t getpid(void); 返回调用进程的PID

pid_t getppid(void); 返回父进程的PID(创建调用进程的进程)

2、创建和终止进程

进程总是处于下面三种状态之一:运行;停止:被挂起且不会被调度;终止:永远停止
终止的原因:


1.收到信号,默认行为为终止进程
2.从主程序返回
3.调用exit函数
父进程通过调用fork函数来创建一个新的运行子进程。fork函数定义如下:#include <sys/types.h>
#include <unistd.h>pid_t fork(void);

fork函数只被调用一次,但是会返回两次:父进程返回子进程的PID,子进程返回0.如果失败返回-1
调用fork函数n次,产生2的n次方个进程。

终止进程用exit函数:


#include <stdlib.h>void exit(int status);

exit函数以status退出状态来终止进程

3、回收子进程

进程终止后还要被父进程回收,否则处于僵死状态。

如果父进程没有来得及回收,内核会安排init进程来回收他们。init进程的PID为1.

一个进程可以通过调用waitpid函数来等待它的子进程终止或停止。waitpid函数的定义如下:


#include <sys/types.h>
#include <sys/wait.h>pid_t waitpid(pid_t pid, int *status, int options);

成功返回子进程PID,如果WNOHANG,返回0,其他错误返回-1.

判断等待集合的成员——pid:

•pid>0:等待集合是一个单独子进程,进程ID等于pid

•pid=-1:等待集合是由父进程所有的子进程组成

•其他

修改默认行为——options:

888584-20161127183549862-343351516.png

检查已回收子进程的退出状态——status,在wait.h头文件中定义了解释status参数的几个宏:

•WIFEXITED:如果子进程通过调用exit或一个返回正常终止,就返回真

•WEXITSTATUS:返回一个正常终止的子进程的退出状态。只有在WIFEXITED返回为真时,才会定义这个状态

•WIFSIGNALED:如果子进程是因为一个未被捕获的信号终止的,那么返回真

•WTERMSIG:返回导致子进程终止的信号的编号。只有在WIFSIGNALED返回为真时才定义这个状态

•WIFSTOPPED:如果引起返回的子进程当前是被停止的,那么返回真

•WSTOPSIG:返回引起子进程停止的信号的数量。只有在WIFSTOPPED返回为真时才定义这个状态

错误条件:如果调用进程没有子进程,那么waitpid返回-1,并且设置errno为ECHILD。

如果waitpid被一个信号中断,那么他返回-1,并且设置errno为EINTR。

wait函数是waitpid函数的简单版本,wait(&status)等价于waitpid(-1,&status,0).成功返回子进程pid,出错返回-1:


#include <sys/types.h>
#include <sys/wait.h>pid_t wait(int *status);

4、让进程休眠

sleep函数使一个进程挂起一段指定的时间。定义如下:


#include <unistd.h>signed int sleep(unsigned int secs);

返回值是剩下还要休眠的秒数,如果到了返回0.

pause函数让调用函数休眠,直到该进程收到一个信号:


#include <unistd.h>int pause(void);

5、加载并运行程序——execve函数

execve函数调用一次,从不返回:


#include <unistd.h>int execve(const char *filename, const char *argv[], const char *envp[]);

成功不返回,失败返回-1.

getnev函数在环境数组中搜寻字符串"name=value",如果找到了就返回一个指向value的指针,否则返回null:


#include <stdlib.h>char *getenv(const char *name);

若存在则为指向name的指针,无匹配是null

setenv和unsetenv函数:如果环境数组包含"name=oldvalue"的字符串,unsetenv会删除它,setenv会用newvalue代替oldvalue,只有在overwrite非零时成立。

如果name不存在,setenv会将"name=newvalue"写进数组。

#include <stdlib.h>int setenv(const char *name, const char *newvalue, int overwrite);
若成功返回0,错误返回-1
    void unsetenv(const char *name);

无返回值

fork函数和execve函数的区别

•fork函数是创建新的子进程,是父进程的复制体,在新的子进程中运行相同的程序,父进程和子进程有相同的文件表,但是不同的PID

•execve函数在当前进程的上下文中加载并运行一个新的程序,会覆盖当前进程的地址空间,但是没有创建一个新进程,有相同的PID,继承文件描述符。

信号

1、信号术语

传递一个信号到目的进程的两个步骤:发送信号和接收信号。
发送信号的原因:


1.内核检测到一个系统事件2.一个进程调用了kill函数,显式的要求内核发送一个信号给目的进程。
一个进程可以发送信号给它自己。

接收信号:


1.忽略2.终止3.执行信号处理程序,捕获信号

待处理信号:

•只发出没有被接收的信号

•任何时刻,一种类型至多只会有一个待处理信号,多的会被直接丢弃

•一个进程可以选择性的阻塞接受某种信号,被阻塞仍可以被发送,但是不会被接收

•一个待处理信号最多只能被接收一次。

•pending:待处理信号集合

•blocked:被阻塞信号集合。

2、发送信号——基于进程组

进程组:

•每个进程都只属于一个进程组。

•进程组ID:正整数

•一个子进程和他的父进程属于同一进程组。

•查看进程组id:getpgrp

•修改进程组:setpgid

/bin/kill程序可以向另外的进程发送任意的信号,格式是:

/bin/kill -n m

n是信号,m是进程或进程组

当n>0时,发送信号n到进程m

当n<0时,使信号|n|发送到进程组m中的所有进程。

进程通过调用kill函数发送信号给其他进程。

进程可以通过调用alarm函数向它自己发送SIGALRM信号


#include <unistd.h>unsigned int alarm(unsigned int secs);

返回前一次闹钟剩余的秒数,若没有返回0.

非本地跳转

c语言中,用户级的异常控制流形式,通过setjmp和longjmp函数提供。

setjump函数在env缓冲区中保存当前调用环境,以供后面longjmp使用,并返回0.

longjmp函数从env缓冲区中恢复调用环境,然后触发一个从最近一次初始化env的setjmp调用的返回。

然后setjmp返回,并带有非零的返回值retval

注:setjmp函数只被调用一次,但返回多次;longjmp函数被调用一次,但从不返回。
操作进程的工具

STRACE:打印一个正在运行的程序和他的子程序调用的每个系统调用的痕迹

PS:列出当前系统中的进程,包括僵死进程

TOP:打印出关于当前进程资源使用的信息

PMAP:显示进程的存储器映射

实践学习总结

数组指针、指针数组、函数指针、指针函数的区别

1.指针数组是数组,数组里的元素是指针

int *daytab[13]

2.数组指针是指针,指向一个类型和元素个数都固定的数组

int (*daytab1)[13]

3.指针函数是函数,返回值类型是指针

int *comp()

4.函数指针是指针,指向函数的指针,函数名就是函数指针

int (*comp1)()

关于exec.1

exec1.c代码运行如下

888584-20161127214302893-2130326793.png

exec1.c中execvp()会从PATH 环境变量所指的目录中查找符合参数file 的文件名,找到后便执行该文件,然后将第二个参数argv传给该欲执行的文件
如果执行成功则函数不会返回,执行失败则直接返回-1,失败原因存于errno中

exevp函数调用成功没有返回,所以没有打印出“* * * ls is done. bye”这句话

想要更深入的理解这段代码,于是将ls -l变换成man -k,修改代码

重新编译运行结果如下

888584-20161127214355409-556977483.png

结果同样也是执行了man -k语句,还是没有返回“* * * man is done. bye”

关于exec2.c

exec2.c代码运行如下

888584-20161127214427550-1318112897.png

exec2与exec1的区别就在于exevp函数的第一个参数,exec1传的是ls,exec2直接用的arglist[0],不过由定义可得这两个等价,所以运行结果是相同的

若将exevp函数传入的arglist[0]改为arglist[1],此时exevp函数没有调用成功,于是打印出“* * * ls is done. bye”这句话

关于exec3.c

exec3.c代码运行如下

888584-20161127214509096-394675688.png

函数中execlp()会从PATH 环境变量所指的目录中查找符合参数file的文件名,找到后便执行该文件,然后将第二个以后的参数当做该文件的argv[0]、argv[1]……最后一个参数必须用空指针(NULL)作结束

以下四个函数中任意一个的运行结果都与其他三个完全一致。

execv()``execvp()``execvpe()``execlp()

关于forkdemo1.c

forkdemo1.c代码先是打印进程pid,然后调用fork函数生成子进程,休眠一秒后再次打印进程id,这时父进程打印子进程pid,子进程返回0
运行结果如下

888584-20161127214750518-1349559149.png

关于forkdemo2.c

这个代码调用两次fork,一共产生四个子进程,所以会打印四个aftre输出
代码运行如下

888584-20161127214808768-2142930242.png

关于forkdemo3.c

fork产生子进程,父进程返回子进程pid,不为0,所以输出父进程的那句话,子进程返回0,所以会输出子进程那句话
运行如下

888584-20161127214834081-227392619.png

关于forkdemo4.c

先打印进程pid,然后fork创建子进程,父进程返回子进程pid,所以输出parent一句,休眠十秒;子进程返回0,所以输出child与之后一句
运行如下

888584-20161127214854628-839395297.png

关于forkgdb.c

父进程打印是先打印两句,然后休眠一秒,然后打印一句,子进程先打印一句,然后休眠一秒,然后打印两句。并且这两个线程是并发的,所以可以看到在一个线程休眠的那一秒,另一个线程在执行,并且线程之间相互独立互不干扰
运行如下

888584-20161127214914378-2093613587.png

888584-20161127214931596-1238092009.png

关于waitdemo1.c

waitdemo1.c的功能是如果有子进程,则终止子进程,成功返回子进程pid。运行如下

888584-20161127215058331-1012952885.png

关于waitdemo2.c

waitdemo2.c比起1来就是多了一个子进程的状态区分,把状态拆分成三块,exit,sig和core
运行如下

888584-20161127215114534-1771817999.png

关于testbuf

testbuf1.c代码运行如下

888584-20161127215143550-1220931993.png

testbuf2.c代码运行如下

888584-20161127215202925-1431942690.png

testbuf1.c和testbuf2.c代码运行结果一致,因为fflush(stdout)的效果和换行符\n是一样的

testbuf3.c将内容格式化输出到标准错误、输出流中

888584-20161127215218284-1188495803.png

testpid.c代码输出当前进程pid和当前进程的父进程的pid

888584-20161127215241206-78978101.png

testsystem.c代码中system()——执行shell命令,也就是向dos发送一条指令。这里是后面可以跟两个参数,然后向dos发送这两个命令,分别执行
如下图,输入ls和dir两个指令后,可以看到分别执行了

888584-20161127215300346-1596748216.png

关于psh1.c

psh1.c代码的效果是输入要执行的指令,回车表示输入结束,然后输入的每个参数对应到函数中,再调用对应的指令
运行结果如下

888584-20161127215418003-1851987117.png

关于psh2.c

psh2.c比起1来,多了循环判断,不退出的话就会一直要你输入指令,并且对于子程序存在的状态条件
运行如下

888584-20161127215433143-1148593653.png

关于signal

sigdemo1.c程序连续输出五个hello,每两个之间的间隔时间为2秒,且在此期间输入的Ctrl+C都被处理成打印OUCH

888584-20161127215453784-359246765.png

sigdemo2.c一直输出haha,按Ctrl+C不能停止

888584-20161127215514393-1399123802.png

sigactdemo2.c休息seconds秒后返回;或者被信号中断且信号处理函数返回后sleep()返回0。所以如果不计较返回值的话,pause()的功能相当于无限期的sleep()

888584-20161127215606909-532192732.png

sigdemo2.c中:

SIG_DFL,SIG_IGN 分别表示无返回值的函数指针,指针值分别是0和1,这两个指针值逻辑上讲是实际程序中不可能出现的函数地址值。
SIG_DFL:默认信号处理程序
SIG_IGN:忽略信号的处理程序

sigdemo3.c根据代码,在read函数不发生错误的情况下输入什么,就输出什么,输入的Ctrl+C也无法终止程序,只有输入quit的时候才会退出

sigactdemo.c中sigaction()会依参数signum指定的信号编号来设置该信号的处理函数。参数signum可以指定SIGKILL和SIGSTOP以外的所有信号

int sigaction(int signum,const struct sigaction *act ,struct sigaction *oldact);


SA_RESETHAND:当调用信号处理函数时,将信号的处理函数重置为缺省值SIG_DFL
SA_RESTART:如果信号中断了进程的某个系统调用,则系统自动启动该系统调用
SA_NODEFER :一般情况下, 当信号处理函数运行时,内核将阻塞该给定信号。但是如果设置SA_NODEFER标记, 那么在该信号处理函数运行时,内核将不会阻塞该信号

学习过程中的问题和解决过程

教材学习中遇到的问题

对于教材中信号方面的代码不太理解。

实践中遇到的问题

编译forkdemo1.c的时候出错,根据提示修改源代码,加入#include <stdio.h>重新编译即可

代码托管截图

888584-20161127220028393-1835885418.png

代码统计

888584-20161127220059081-1317032178.png

代码链接:(https://git.oschina.net/xzhkuma1128/CSAPP2E)

心得体会

本周内容比较多,不仅是课本知识更要花时间实践,对于代码的理解还有些问题,看了书对于信号这部分真的不太理解,对于fork()函数因为老师上课时有讲解,所以再看书就觉得好理解多了,希望老师能再讲讲信号这部分知识。

学习进度条

博客量(新增/累积)学习时间(新增/累积)重要成长
目标30篇400小时
第一周1/120/20学习了Linux核心命令
第二周1/221/41学习了vim、gcc、gdb指令
第三周1/320/61学习了信息的表示和处理,了解了二进制在计算机系统中的重要性
第五周1/420/81学习了机器级程序,读懂汇编代码
第六周1/519/100了解了处理器对于指令的处理过程
第七周1/618/118了解了存储器层次结构及存储技术
第八周2/815/133对前几周内容进行复习
第十周3/1210/148学习Linux重要命令
第十一周2/1415/163学习异常控制相关知识

转载于:https://www.cnblogs.com/xzh20145231/p/6106980.html

相关文章:

JAR命令使用

jar 命令详解 jar 是随 JDK 安装的&#xff0c;在 JDK 安装目录下的 bin 目录中&#xff0c;Windows 下文件名为 jar.exe&#xff0c;Linux 下文件名为 jar。它的运行需要用到 JDK 安装目录下 lib 目录中的 tools.jar 文件。不过我们除了安装 JDK 什么也不需要做&#xff0c;因…

捍卫者usb管理控制系统_捍卫超模块化JavaScript

捍卫者usb管理控制系统by Mike Groseclose通过Mike Groseclose 捍卫超模块化JavaScript (In Defense of Hyper Modular JavaScript) Last week npmgate was a big topic for the JavaScript community. For those of you who haven’t been following what happened, here’s …

Android开发——布局性能优化的一些技巧(一)

0. 前言上一篇我们分析了为什么LinearLayout会比RelativeLayout性能更高&#xff0c;意义在于分析了这两种布局的实现源码&#xff0c;算是对一个小结论的证明过程&#xff0c;但是对布局性能的优化效果&#xff0c;对这两种布局的选择远不如减少布局层级、避免过分绘制、按需加…

1-RAC基础

1 安装 pod ‘ReactiveObjC’ RAC 其实大大减少了代码量 2 基本使用 // 0 RAC 中最为常见的类 信号类/*RACSignal&#xff1a;信号类1.通过RACSignal 创建1个信号&#xff08;默认&#xff1a;冷信号&#xff09;2.通过订阅者&#xff0c;订阅信号信号&#xff08;变成:热信号…

static用法总结

C的static有两种用法&#xff1a;面向过程程序设计中的static和面向对象程序设计中的static。前者应用于普通变量和函数&#xff0c;不涉及类&#xff1b;后者主要说明static在类中的作用。 一、面向过程设计中的static1、静态全局变量2、静态局部变量3、静态函数二、面向对象的…

小程序 缩放_缩放流星应用程序的初体验

小程序 缩放by Elie Steinbock埃莉斯坦博克(Elie Steinbock) 缩放流星应用程序的初体验 (First Experiences Scaling a Meteor App) I recently went through the challenge and ordeal of having to scale my Meteor app. It’s a project that had already been running in …

SQL Server Lock Escalation - 锁升级

Articles Locking in Microsoft SQL Server (Part 12 – Lock Escalation) http://dba.stackexchange.com/questions/12864/what-is-lock-escalation 2008 R2 Lock Escalation (Database Engine)---Forward from Locking in Microsoft SQL Server (Part 12 – Lock Escalation)…

Jzzhu and Chocolate

CF#257 div2 C:http://codeforces.com/contest/450/problem/C 题意&#xff1a;n*m的方格&#xff0c;每次可以横着或者纵向的切一刀&#xff0c;问切k之后&#xff0c;最小的最大是多少。 题解&#xff1a;比赛的时候没有想到怎么处理&#xff0c;看了别人的题解&#xff0c;才…

2-RACommand

RACommand RACCommand 就是命令 // RACCommand 就是命令// 0 创建一个CMD 穿进去一个用于构建RACSignal的Block参数来初始化RACommandRACCommand *cmd [[RACCommand alloc]initWithSignalBlock:^RACSignal * _Nonnull(id _Nullable input) {// 此处是cmd 执行的输入源NSLog(…

玻璃上的编码喜悦(+ 10史诗般的Epigrams)

by Den McHenry丹麦克亨利(Den McHenry) 玻璃上的编码喜悦( 10史诗般的Epigrams) (Perlis on Coding Joy ( 10 Epic Epigrams)) Alan J. Perlis was the first recipient of the Turing Award. He’s possibly most remembered today for his Epigrams on Programming, which …

【Android】Activity生命周期(亲测)

测试手机&#xff1a;Nexus 5 系统&#xff1a;4.4 一、测试 测试代码&#xff1a; 1 package com.example.androidalarm;2 3 import android.app.Activity;4 import android.content.Context;5 import android.content.res.Configuration;6 import android.os.Bundle;7 impo…

angularjs 学习笔记 简单基础

angularjs是谷歌公司的一个项目&#xff0c;弥补了hml在构建方面的不足&#xff0c;通过指令&#xff08;directive&#xff09;来扩展html标签&#xff0c;可以使开发者使用html来声明动态内容。 angularjs主要用来开发单页应用&#xff08;SPA&#xff09;为主的项目。 angul…

3-RACSignal 常用方法

RACSingal的常用方法 一 基本使用 1map // 0 创建信号提供者// RACSubject&#xff0c;既能发送信号&#xff0c;又能订阅信号// 多用于代理&#xff0c;相当于OC里的delegate或者回调blockRACSubject *subject [RACSubject subject];// 1 绑定信号RACSignal *bindSignal …

javascript迭代_探索JavaScript迭代

javascript迭代by Festus K. Yangani由Festus K.Yangani 探索JavaScript迭代 (Exploring JavaScript Iteration) Loops allow programs to perform repetitive tasks, such as iterating through an array, while adhering to the DRY principle (Don’t Repeat Yourself). Th…

4 RACMulticastConnection 连接类

# RACMulticastConnection信号被多次订阅如果一个信号多次被订阅&#xff0c;那么代码块代码会多次被执行。objective-c// 创建信号RACSignal *sg1 [RACSignal createSignal:^RACDisposable * _Nullable(id<RACSubscriber> _Nonnull subscriber) {NSLog("网络请求…

ie6下常见的bug 调整页面兼容性

ie6下常见的bug 我们布局页面&#xff0c;首先符合标准&#xff0c;如何写一个页面的标准性&#xff1f; 但是ie6等浏览器本身就比较特殊&#xff0c;bug比较多&#xff0c;兵法云&#xff0c;知己知彼百战百胜。我们需要了解ie6的一些常见bug&#xff0c;这样&#xff0c;更好…

Cacti安装详细步骤

Cacti安装详细步骤 前提LNMP或LAMP架构已搭建完成 一、cacti概述 1. cacti是用php语言实现的一个软件&#xff0c;它的主要功能是用snmp服务获取数据&#xff0c;然后用rrdtool储存和更新数据&#xff0c;当用户需要查看数据的时候用rrdtool生成图表呈现给用户。因此&#xff0…

为什么使用单页应用_为什么我讨厌您的单页应用

为什么使用单页应用by Stefan Tilkov斯蒂芬蒂尔科夫(Stefan Tilkov) 为什么我讨厌您的单页应用 (Why I hate your Single Page App) Okay, now that I have your attention, let me say that I don’t really hate your single page app. I just find it highly annoying, unl…

marquee实现文字移动效果;js+div实现文字无缝移动效果

1.marquee实现文字移动&#xff1a; <marquee width"220px;" scrollamount"5" onmouseover"this.stop()" onmouseout"this.start()" ><p style"letter-spacing:2px;width: 1px;">欢迎您登录拜博医疗口腔集团内部…

URAL 1203 Scientific Conference(贪心 || DP)

Scientific Conference 之前一直在刷计算几何&#xff0c;邀请赛连计算几何的毛都买见着&#xff0c;暑假这一段时间就做多校&#xff0c;补多校的题目&#xff0c;刷一下一直薄弱的DP。多校如果有计算几何一定要干掉-。- 题意&#xff1a;给你N个报告会的开始时间跟结束时间&a…

5- RAC 集合 RACTuple RACSequence

RAC 集合 RACTuple RACSequence // 0 RACTuple 就是一个数组/*RACTuple 就是一个数组*/RACTuple *tp1 [RACTuple tupleWithObjects:"5",5,1, nil];RACTuple *tp2 [RACTuple tupleWithObjectsFromArray:["11","22","33"]];NSLog(&quo…

测试开发人员与开发人员_如何升级为开发人员

测试开发人员与开发人员by Will Hughes威尔休斯(Will Hughes) 如何升级为开发人员 (How to Level up as a Developer) Being a productive developer is something you can learn through experience, books, or trial and error. But, one of the best ways to become a prod…

ORA-00959: tablespace 'PSAPTEMP' does not exist

错误 : ORA-00959: tablespace PSAPTEMP does not exist 解决办法: CREATE TEMPORARY TABLESPACE PSAPTEMP TEMPFILE E:/Oracle/ORC/sapdata3/temp_1/temp.data1 SIZE 500M REUSE AUTOEXTEND ON NEXT 100M MAXSIZE unlimited EXTENT MANAGEMENT LOCAL UNIFORM SIZE 1M;ALTER …

RAC rac_liftSelector

RAC rac_liftSelector 主要是用于线程的同步 - (void)viewDidLoad {[super viewDidLoad];// Do any additional setup after loading the view, typically from a nib.// rac_liftSelector// 类似于dispatch_group 中的组// 多线程中的组 等所有的请求都完毕之后 去更新UIRAC…

随笔记一些莆田话

莆田话是闽南话和福州话混合的产物&#xff0c;当然也是古汉语保留至今的珍宝。很多莆田话的词语是有源可溯的。这里记录一些平常想到的又可能不为人知的词语。 莆田话——普通话解释 物件——东西 万代——很多 先生——老师&#xff08;先生白读时是老师的意思&#xff09;&a…

JavaScript库和API

by Adam Recvlohe通过亚当雷夫洛厄(Adam Recvlohe) API就像一盒巧克力 (APIs are like a box of chocolates) If you have written JavaScript for the DOM before, then you probably know how unwieldy it can get. I mean getElementById is seven syllables and 14 charac…

Hadoop 全分布模式 平台搭建

现将博客搬家至CSDN&#xff0c;博主改去CSDN玩玩~ 传送门&#xff1a;http://blog.csdn.net/sinat_28177969/article/details/54138163 Ps&#xff1a;主要答疑区在本帖最下方&#xff0c;疑点会标注出来。个人在配置过程中遇到的困难都会此列举。 实验介绍&#xff1a; 本次实…

iOS 使用fastlane自动化打包步骤

加粗样式### iOS 使用fastlane 自动打包步骤 &#xff01;参考 1 查看ruby版本信息 本机是否安装ruby ruby -v 2 安装xcode命令行工具 点击同意即可 xcode-select --install 3 安装fastlane 键入如下命令 sudo gem install fastlane -NV4 使用 1 打开终端 cd 进入到要打包的…

今天开始搞CentOS 7

今天开始搞CentOS 7,安装过程很顺利&#xff0c;界面相当友好。转载于:https://www.cnblogs.com/lixd/p/3868649.html

java ruby_Java,Ruby和Go,我的天哪!

java rubyFree Code Camp has focused 100% on full stack JavaScript since we started 17 months ago. We’ve taught JavaScript on the front end, JavaScript on the back end (thanks to the powerful Node.js framework) — and even JavaScript as a database querying…