习题
1、首先是按照税率找到刚好税率最好的情况。这里用二分。
int a[100] = { 2200, 2700, ....}
double c[100] = {0, 0.14, 0.15, 0.16, ...}
首先用二分找最刚好比其小的那个数
int bs(int *a, int b, int e, int v)
{
int *begin = a + b, int *end = a + e, *mid;
if (!a || b >= e) return -1;
while (begin < end)
{
mid = begin + ((end - begin) >> 1);
if (*mid > v) end = mid;
else if (*mid < v) begin = mid + 1;
else return mid - a;
}
while (*mid > v) --mid;
return mid - a;
}
然后
int iter = bs(a, 0, 100, v);
double tax = (money - a[iter]) * c[iter+1];
2、求多项式系数
y = a[n];
for (i = n - 1; i >= 0; --i)
y = x * y + a[i];
3、略过,网上见到过源代码
4、日期处理
这里把所有相关的处理函数放出来。
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int days[12] = {31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
typedef struct _date
{
int year, month, day;
}date;
//看是否是闰年
int leap(int year)
{
return (0 == year % 4 && year % 100) || year % 400 == 0;
}
//看是时间是否有效
int legal(date a)
{
if (a.month <0 || a.month > 12) return 0;
if (a.month == 2) return a.day > 0 && a.day <= (28 + leap(a.year));
return a.day >0 && a.day <= days[a.month -1];
}
//比较时间
int datecmp(date a, date b)
{
if (a.year != b.year) return a.year - b.year;
if (a.month != b.month) return a.month - b.month;
return a.day - b.day;
}
//计算周几?
int weekday(date a)
{
int tm = a.month >= 3 ? (a.month - 2) : (a.month + 10);
int ty = a.month >= 3 ? (a.year) : (a.year - 1);
return (ty + ty/4 - ty/100 + ty/400 + (int)(2.6 * tm - 0.2) + a.day) % 7;
}
//时间化为天数
int date2int(date a)
{
int i ;
int ret = a.year * 365 + (a.year - 1) / 4 - (a.year -1) / 100 + (a.year - 1) / 400;
days[1] += leap(a.year);
for (i = 0; i < a.month - 1; ret += days[i++]);
days[1] = 28;
return ret + a.day;
}
//天数化为时间
date int2date(int a)
{
date ret;
int i = 0;
ret.year = a/146097*400;
for (a %= 146097; a >= 365+leap(ret.year);
a -= 365 + leap(ret.year), ret.year++);
days[i] += leap(ret.year);
for (ret.month = 1; a >= days[ret.month - 1]; a -= days[ret.month - 1], ret.month++);
days[1] = 28;
ret.day = a + 1;
return ret;
}
//计算距离
int dist(date a, date b)
{
int ad = date2int(a);
int bd = date2int(b);
return ad - bd > ? ad - bd : bd - ad;
}
//生成日历
void cal(date a)
{
int i, w, j, k;
a.day = 1;
if (a.month == 2) { k = days[a.month - 1] + leap(a.year);}
else k = days[a.month - 1];
printf(" %2d月%4d年 \n", a.month, a.year);
printf("日 一 二 三 四 五 六\n");
w = weekday(a);
i = w % 7; while (i--) printf(" "); printf("%2d", 1);
if (w % 7 == 6) printf("\n"); ++w;
for (i = 1; i <= k; ++i, w = (w + 1) % 7)
{
if (w % 7 == 0) printf("%2d", i);
else printf(" %2d", i);
if (w % 7 == 6) printf("\n");
}
}
第5题,解法是hash表中带hash。第一个以ic, tic 等做hash
首先根据后缀找到hash_set,再把余下的字段,依次在hash_set中查找,并取出最长的。
#include<stdio.h>
#include<stdlib.h>
#include<string>
#include<iterator>
#include<iostream>
#include<algorithm>
#include<hash_map>
#include<hash_set>
using namespace std;
using namespace stdext;
char *p[] = {"et-ic", "al-is-tic", "s-tic", "p-tic", "-lyt-ic", "ot-ic", "an-tic",
"n-tic", "c-tic", "at-ic", "h-nic", "n-ic", "m-ic", "l-lic", "b-lic", "-clic", "l-ic",
"h-ic", "f-ic", "d-ic", "-bic", "a-ic", "-mac", "i-ac"};
void build_map(hash_map<string, hash_set<string> >& dict)
{
const int n = sizeof(p)/ sizeof(char *);
for (int i = 0; i < n; ++i)
{
string line = p[i]; reverse(line.begin(), line.end());
int pos = line.find('-');
dict[line.substr(0, pos)].insert(line.substr(pos + 1, line.length() - pos - 1));
}
}
string lookup(hash_map<string, hash_set<string> >& dict, string word)
{
string line = word; reverse(line.begin(), line.end());
int pos = line.find('-');
string ret;
hash_map<string, hash_set<string> >::iterator iter;
if (dict.end() != (iter = dict.find(line.substr(0, pos))))
{
hash_set<string> &h = iter->second;
string temp = line.substr(pos + 1, line.length() - pos - 1);
for (int j = 1; j <= temp.length(); ++j)
{
string c = temp.substr(0, j);
if (h.find(c) != h.end() && c.length() > ret.length())
ret = c;
}
}
ret = iter->first + "-" + ret;
reverse(ret.begin(), ret.end());
return ret;
}
int main(void)
{
string sline;
hash_map<string, hash_set<string> > dict;
build_map(dict);
while (cin >> sline)
{
cout << lookup(dict, sline) << endl;
}
return 0;
}
6、这个可以用python来写,下面先看一下示例代码。
模板文件/tmp/win03.domain.template
;SetupMgrTag
[Unattended]
[GuiUnattended]
AdminPassword=${admin_password}
EncryptedAdminPassword=NO
OEMSkipRegional=1
[UserData]
ComputerName=${computer_name}
代码
import os
Template = None
if Template is None:
t = __import__('Cheetah.Template', globals(), locals(),
['Template'], -1)
Template = t.Template
fp = open('/tmp/unattend.xml', 'w')
tem = open('/tmp/win03.domain.template').read()
domain_list = {'computer_name': 'computer',
'admin_password': 'admin',
'Use':'Use'}
info = str(Template(tem, searchList=[domain_list]))
fp.write(info)
fp.close()
如果采用C++实现,并且${}里面的代单词表明是要被替换的单词。那么处理方法如下:
void Template(char *fname, char *temp_fname, map<string, string>& dict)
{
ofstream output(fname);
ifstream temp(temp_fname);
string line;
while (getline(temp, line, '\n'))
{
int bpos = 0;
string::size_type pos = 0;
while (string::npos != (pos = line.find("${", bpos)))
{
string::size_type epos = line.find("}", pos);
string t = line.substr(pos + 2, epos - pos - 2);
cout << t << endl;
map<string, string>::iterator iter = dict.find(t);
if (dict.end() != iter)
{
line.replace(pos, epos - bpos + 1, iter->second);
bpos += iter->second.length();
}
else
{
bpos = epos + 1;
}
}
output << line << "\n\r";
}
temp.close();
output.close();
}
7、略去,比较扯
8、2^16 = 65536个数。所以5个七段显示器肯定是够用的。
首先可以预处理一下,把0 = {0, 2, 3, 4, 5, 6}相应的8个bit置1之后的值保存到一个数组中。
char rec[10];
char temp[7];
char *get(int n)
{
int iter = 5;
memset(temp, 0, sizeof(temp));
while (n)
{
temp[iter--] = rec[n % 10];
n /= 10;
}
while (iter>= 0) { temp[iter] = rec[0]; iter --;}
return temp;
}