Xcode 4 关闭代码符号索引
随着工程不断变大,Xcode消耗的资源越来越多,主要是Xcode代码补全等功能需要对项目中所有的符号进行索引。在终端中运行下面的命令可以关闭索引功能,当然一些依赖它的功能也会受到影响。
defaults write com.apple.dt.XCode IDEIndexDisable 1
随着工程不断变大,Xcode消耗的资源越来越多,主要是Xcode代码补全等功能需要对项目中所有的符号进行索引。在终端中运行下面的命令可以关闭索引功能,当然一些依赖它的功能也会受到影响。
defaults write com.apple.dt.XCode IDEIndexDisable 1
在iPhone上实现了一个简单的http服务器,希望能够将html文档或图片等传到iPhone上以便随时查看。用户可以通过iTunes将文件传到应用沙盒的Documents下面,但iTunes传输只能传文件,无法传目录结构。于是想到将文件打包成zip文件传到沙盒里。本想zip文件应该用zlib就可以搞定的,结果Google了一番,好像不行。于是找到了这个zziplib,实现了根据访问路径自动从zip文件读取对应文件输出,下面是相关代码:
std::size_t second_slash_pos = request_path.find_first_of("/", 1);
if (second_slash_pos == std::string::npos) {
printf("%s file not found\n",request_path.c_str());
return;
}
std::string first_component_name = request_path.substr(0,second_slash_pos);
std::string zip_path = doc_root_ + first_component_name + ".zip"; //根据请求路径计算对应zip文件路径
ZZIP_DIR* dir = zzip_dir_open((char *)zip_path.c_str(),NULL); //打开zip文件
if (dir) {
std::string path = request_path.substr(second_slash_pos+1); //得到请求文件对应的zip文件里面的路径
if (path == "") {
path="index.html";
}
ZZIP_FILE* fp = zzip_file_open(dir,(char *)path.c_str(),NULL); //打开请求的文件
if (fp) {
char buf[512];
zzip_ssize_t len;
while((len = zzip_file_read(fp,buf, 512))) { //读取文件流到缓冲区
rep.content.append(buf, len); //将缓冲区内容添加到输出
}
zzip_file_close(fp);
}else{
zzip_dir_close(dir);
printf("%s file not found\n",request_path.c_str());
return;
}
zzip_dir_close(dir);
}else{
printf("%s file not found\n",request_path.c_str());
return;
}
此外,zzip还提供磁盘和内存盘映射的接口,以下代码使用内存盘映射实现相同的功能:
std::size_t second_slash_pos = request_path.find_first_of("/", 1);
if (second_slash_pos == std::string::npos) {
printf("%s file not found\n",request_path.c_str());
return;
}
std::string first_component_name = request_path.substr(0,second_slash_pos);
std::string zip_path = doc_root_ + first_component_name + ".zip"; //根据请求路径计算对应zip文件路径
ZZIP_MEM_DISK *disk = zzip_mem_disk_open((char *)zip_path.c_str());
if (disk) {
std::string path = request_path.substr(second_slash_pos+1);
if (path == "") {
path="index.html";
}
ZZIP_DISK_FILE* fp = zzip_mem_disk_fopen(disk,(char *)path.c_str());
if (fp) {
char buf[512];
zzip_ssize_t len;
while((len = zzip_mem_disk_fread(buf, 1, 512,fp))) {
rep.content.append(buf, len);
}
zzip_mem_disk_fclose(fp);
}else{
zzip_mem_disk_close(disk);
printf("%s file not found\n",request_path.c_str());
return;
}
zzip_mem_disk_close(disk);
}else{
printf("%s file not found\n",request_path.c_str());
return;
}
使用内存盘映射可以提高程序性能,但是需要消耗大量内存,在iPhone上不适用。
在找零算法(1)中,笔者给出了问题的思路和相应的实现代码,但是不能完整地解决问题。文中也提到了特例情况。本文将进一步解决此问题。
对于第一个问题,显然不能再用贪心法一次找到最优解,需要对找到的解进行测试是否刚好满足。这次笔者采用了与上篇文中第二个问题类似的算法,只是返回的值是硬币数量而不是方法数量。具体代码:
int a[]={50,20,10,5,2};
int minCountOfCoins(int n,int index){
if(n==0) return 0;
if (index==5) {
return -1; //无法找到正好满足的解
}
int num = a[index]; //当前计算的面值
++index;
int count = n/num; //当前面值最大数量
int v = n%num; //还剩下的无法用当前面值找开的钱数
int result = 0;
int i;
for(i = 0;i<=count;++i){
if((result=minCountOfCoins(v+num*i, index)) >= 0)
break;
}
if (result<0) { //没有满足的找零方式
if (count==0) { //没有更多的方式了
return 0;
}
return -1; //返回-1表示当前方式无法找到满足的找零方式,还可以继续测试其它方式
}
return result+count-i; //返回钱的张数
}
第二个问题虽然也有问题,但无需大的改变,只需要调整一下边界检测条件。具体代码:
int a[]={50,20,10,5,2};
int kindOfMethod(int n, int index){
if(n==0) return 1;
if (index==5) {
return 0; //此方式不能满足条件
}
int num = a[index];
++index;
int count = n/num;
int v = n%num;
int result = 0;
int i;
for(i = 0;i<=count;++i){
result += kindOfMethod(v+num*i, index);
}
return result;
}
至此找零算法已经完成,对于钱币的找零不会有什么错误的地方了,但是对于一些更一般化的东西,假设存在1,2,6,7,10几种硬币,要找13个单位的零钱,按照这里的算法最少硬币数量的结果就会是3,而我们一眼就能看出应该是2。所以读者如果有兴趣,可以尝试更进一步解决此类问题。
问题描述:现存在一堆面值为 V1、V2、V3 … 个单位的零钱,需要找出总值为N个单位的零钱。假设这一堆面值分别为 1、2、5、10、20 元,需要找出总值 N为 63 元的零钱。
1、求满足条件的最小硬币数量。
2、求有多少种找法满足条件。
对于第一个问题,最容易想到的是贪心解法:
要找N元钱,先拿N除最大零钱面值,取整就是所找的最大面值零钱的个数,取模得出余数重新赋给N。重复操作直到除最小面值结束。具体代码:
int a[]={20,10,5,2,1};
int minCountOfCoins(int n){
int count = 0;
int i;
for (i=0; i<5; ++i) {
count += n/a[i];
n %= a[i];
}
return count;
}
对于第二个问题,可以采用动态规划:
先对问题进行拆解,要用V1、V2、V3 ... Vn组成N可以拆解成
N/MAX(V)个最大面值的零钱 和 V1、V2、V3 ... Vn-1组成N%MAX(V)之和
上面只是一种拆解方法,其它的拆解方法可以是
N/MAX(V)-i个最大面值的零钱 和 V1、V2、V3 ... Vn-1组成N%MAX(V)+MAX(V)*i之和
当然现在是求方法数,所以结果就是这些拆解方法的数量,而每一个拆解方法又是由它的子问题的拆解方式算出。具体代码:
int a[]={20,10,5,2,1};
int kindOfMethod(int n, int index){
if(index==4) return 1;
if(n==0) return 1;
int num = a[index];
++index;
int count = n/num;
int v = n%num;
int result = 0;
int i;
for(i = 0;i<=count;++i){
result += kindOfMethod(v+num*i, index);
}
return result;
}
上面的算法对于一些特殊情况会有问题,如零钱中只有2、5、10、20这几种面值,再要找出63元的零钱就有问题了。留作下次分析。