2009年3月5日

偏序集的Dilworth定理

摘要: 偏序集的Dilworth定理(转载)2008/04/21 18:48先介绍一下偏序关系:偏序是在集合X上的二元关系≤(这只是个抽象符号,不是“小于或等于”),它满足自反性、反对称性和传递性。即,对于X中的任意元素a,b和c,有:自反性:a≤a;反对称性:如果a≤b且b≤a,则有a=b;传递性:如果a≤b且bX...阅读全文

posted @ 2009-03-05 16:40 woodfish 阅读(965) 评论(0) 编辑

2009年2月21日

XJOJ历经2个月终于完成啦~~

XJ Online Judge System历经2个月终于完成了,其实早在大二上学期末的时候就开始写了,不过当时由于一些原因没能坚持写下去,这学期大三上期末的时候又想写了,于是把原来的程序全部重写了一遍。
系统目前只能运行在Linux系统中,里面使用了少量的QT4的东东,该OJ系统的特色有:
1。采用C/S结构来进行评测,S端只负责取题以及更新状态与客户端交换信息,C端进行全部的评判工作,编译-》运行-》评测等等。C端采用多线程技术,这样C端可以运行在多台机器上,每台机器又可以多线程评测,于是web服务器的压力非常小,并且评测的并发度可以非常大。同时,一个评测线程的意外死亡也不会影响其他的线程。
2。S端取任务不是无限循环的去读取数据库,而是使用了生产者/消费者模型,生产着负责周期性的一次从数据库中取出多个任务丢到任务缓冲池,消费者从任务缓冲池中读取任务发送给C端进行评测。当没有任务时,消费者和C端都会挂起睡眠,这样,对系统的资源利用率会很高。
3。安全性很高,一般考虑了安全性的OJ大多数只是用一个权限非常低的用户来执行用户提交的程序,但是这还远远不够,用户仍然能够提交对系统产生破坏性的程序,比如不停的fork(),本OJ对静态程序(C,C++等)采用了linux内核级别的调试工具ptrace,可以追踪用户程序所有的系统调用,对有危险的系统调用进行截获,从根源上阻止了危险的程序。对于Java程序,采用了一个安全沙箱的技术,将用户提交的程序Main.class动态载入到安全沙箱中以一个线程来运行,这样安全沙箱就可以彻底控制用户程序的运行状况。
4。对Java程序的评测准,一般的OJ把Java程序的运行当作普通的静态程序来运行,这样不仅会导致安全问题,也会使得评测用户程序运行的时间,消耗的内存非常不准确。因为我们知道,Java程序是必须运行在JVM下的,而启动JVM的时间是很长的,JVM所占的内存也是相当大的。本OJ由于采用了上述安全沙箱的方式来运行Java程序,因此可以完全解决这个问题。
5。WEB方面,采用了PHP中很著名的SMARTY模板引擎,对很多页面进行缓存处理,使得服务器的压力进一步减小。

OJ的源代码已经放到 code.google.com上面了,欢迎大叫提建议,提bug哦,更加欢迎大家一起来继续开发(我现在也还在继续完善这个oj,如果有谁对这个感兴趣,想一起开发的,请联系我,我会把SVN发给你~)

 

http://code.google.com/p/xjoj/

 

把代码也放一份到这里,等明天回学校了去机房安装到服务器上再贴出 测试地址 ^_^

xjoj.rar下载

 

贴几个图片:

Client和Server端刚启动,Client连接Server:

 

我提交了一个Java的程序上去,开始评测了:

 

WEB页面(不是很好看...,没办法,没艺术细胞阿)

 

 

posted @ 2009-02-21 01:36 woodfish 阅读(385) 评论(3) 编辑

2008年12月27日

fork()调用的一个趣题

经常看到有人问到这样一个问题:


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

int main() {
  
int pid=0;
  
for(int i=0;i<5;i++) {
    pid
=fork();
    
if(pid==0) {
      printf(
"pid:%d\n",getpid());
    }
  }
  
return 0;
}

问最后打印了多少行pid:xxx.很多人一看,认为很简单,不就产生了5个子进程嘛,答案就是5个,这样回答可以说压根没有理解Linux/Unix中fork()系统调用是怎么实现的。上面的问题等价于问这个程序总共产生了多少个进程(算自身)an,最后的答案就是an-1,因为最开始的进程不会打印这条信息,如果把程序这样改一下:


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

int main() {
  
int pid=0;
  
for(int i=0;i<5;i++) {
    pid
=fork();
    wait(NULL);
  }
  printf(
"pid:%d\n",getpid());
  
return 0;
}

 那么答案很明显就是所有的进程个数an,上面加入wait调用的目的是使各个进程不交叉输出信息。

为了求an,先简要的介绍一下fork()系统调用,在linux中,fork()调用会调用clone(),而clone()最终会调用 do_fork()系统调用来产生子进程,关键是这个子进程怎么产生的。在linux/unix中,fork()产生的子进程相当于复制了整个父进程,首先复制了PCB,然后将内存页表共享到父进程的页面(写时复制)。通俗一点,子进程和父进程看起来是完全一样的,一样的代码段,一样的数据段,一样的进程控制块,但是他们是独立的,并且从内核返回到用户态时,系统调用对原进程返回子进程的pid,对子进程返回0,这样就可以区分父子进程了。

 回到上面的问题,为什么答案5是错的,举个例子:父进程i=0的时候fork()了一个子进程p1,但是p1现在和父进程的状态是一样的,也就是会继续接着循环,从i=1来fork()一个p2,而p2又会继续从i=3开始来fork()其他的子进程,这样就会产生很多很多子进程了。

现在来求解具体的产生的进程的个数。

设f(n)表示程序中循环会执行n次时整个程序会产生的进程数,很容易得到递推公式:

 f(n)=1+f(n-1)+f(n-2)+f(n-3)+...+f(0)

比如for i=0;i<n;i++

因为i=0时fork()的子进程下次会继续循环n-1次,i=1时 fork()的子进程下次会仅需循环n-2 次。。。。

 其中常数1是进程本身。

边界条件,f(0)=1

这样,我们就得到了问题的答案:

f(n)=1+f(n-1)+f(n-2)+...+f(0)

f(0)=1

这个可以求出闭形式:

f(0)=1

f(1)=2

f(2)=4

...

用数学归纳法可以得到f(n)=2^n

所以对于程序一,会打印出2^5-1=31行信息。

对于程序二,总共会产生2^5=32个进程。


posted @ 2008-12-27 23:41 woodfish 阅读(258) 评论(0) 编辑

2008年10月18日

实现google那种输入框提示的功能

摘要: 今天在项目中遇到一个需求,就是在input输入框中录入数据时(名字),如果敲入了一部分,在数据库中存在已有的姓名的前缀与之匹配,就弹出一个 google页面那种效果的下拉框,把相关的姓名列出来供他选择。可以用箭头上下选择,也可以用鼠标选择。这样可以提高录入的效率。 输入框的布局如下: 最终的效果如下: 表单中输入框的html代码为:[代码]为了在输入一些内容时,能够显示出那个选择框,我们要建...阅读全文

posted @ 2008-10-18 22:08 woodfish 阅读(1254) 评论(1) 编辑

2008年10月3日

POJ 3691 安徽第二题 有限状态自动机+DP

摘要: http://acm.pku.edu.cn/JudgeOnline/problem?id=3691题目大意是说给定一个长度最大为1000的仅由A,T,C,G四个字符组成的字符串,要求改变最少的字符个数,使得得到的字符串中不含有任意预先给定的一系列子串。一般都会想到用动态规划,但是怎么DP是个问题,怎么设计状态。换个角度,我们要最终的字符串不含有任意模板串,这个涉及到多串匹配的知识。我们知道,可以建...阅读全文

posted @ 2008-10-03 14:56 woodfish 阅读(2061) 评论(8) 编辑

2008年9月20日

哈尔滨赛区网络预选赛总结

摘要: 一共8道题,我们队最后AC了6道,队伍排名29,还不错.刚开始比赛,早上9点,脑袋晕晕的,看了A题,是个计算几何,就是求一个车能否通过一个直角弯道,我画了画图马上觉得直接枚举角度,让车靠着一个顶点旋转就可以了,但是当时脑袋晕晕的,根本写不了代码,于是看B题,发现B题已经有些队过了,看来是个很简单的题目,当时急急的读完题目竟然把题目搞错了,前后写了2个版本的程序都没写下去,后来看有100多个队过了,...阅读全文

posted @ 2008-09-20 23:19 woodfish 阅读(786) 评论(7) 编辑

2008年9月17日

[计算几何]点集中的点能组成多少个正方形

摘要: http://acm.pku.edu.cn/JudgeOnline/problem?id=2002http://acm.pku.edu.cn/JudgeOnline/problem?id=3432枚举正方形一条对角线线上的2个点,很容易求出另外2个点,然后要检查另外2个点是否坐标都是整数,如果都是,然后看这2个点是否在点集中,要快速的判断一个点是否在点集中,可以先把点排序,然后二分查找,或者对点的...阅读全文

posted @ 2008-09-17 00:33 woodfish 阅读(400) 评论(0) 编辑

2008年9月10日

[计算几何]POJ 1375 点对圆的切线+线段重叠

摘要: http://acm.pku.edu.cn/JudgeOnline/problem?id=1375题目大意如上图,ceiling上面有个光源,ceiling和floor有一些圆形的管子,要求出最后floor上光源找不到的区域。比较简单,直接对每个圆求出两条切线,进而求出被这个圆遮挡住的区域(bx,ex)最后把这些区域按bx排序,然后线性扫描一遍就可以得到不相交的区域了。PS:这题精度比较重要,另外...阅读全文

posted @ 2008-09-10 20:13 woodfish 阅读(406) 评论(0) 编辑

2008年9月9日

[计算几何]POJ 1556 判断线段相交+Dijkstra

摘要: http://acm.pku.edu.cn/JudgeOnline/problem?id=1556挺有意思的一个题。 题目大意如上图,有一个房间,要从(0,5)走到(10,5),房间内有一些竖直的墙壁,现在要求最短的路径长度。首先,很直观很显然的,要使路径达到最短,我们每次都是沿着墙的端点按直线走,也就是从一个墙的端点走到另一个墙的端点,这样问题就可以转换为图论中的最短路问题了,设上图中...阅读全文

posted @ 2008-09-09 00:11 woodfish 阅读(663) 评论(0) 编辑

2008年9月8日

[计算几何] POJ 1873 暴力+凸包

摘要: http://acm.pku.edu.cn/JudgeOnline/problem?id=1873题目大意是从一个点集中选出一些点,是这些点的长度之和能够把剩下的点围起来,并且没个点有个权值,要求最后的选出的点的权值之和最小,如果有多个最小的,要求选出的点数最小。由于点集数很小,n<=15,很容易想到枚举,每个点有选与不选2中状态,有2^n选点方式,没枚举一个选点方式,对剩下的点进行Grah...阅读全文

posted @ 2008-09-08 23:16 woodfish 阅读(508) 评论(0) 编辑

导航

<2012年2月>
2930311234
567891011
12131415161718
19202122232425
26272829123
45678910

公告

昵称:woodfish
园龄:5年3个月
粉丝:1
关注:0

搜索

 

随笔分类

随笔档案

技术相关

阅读排行榜

推荐排行榜