数据结构定义
#define maxn 1010
#define Datatype int
struct Seqlist{
Datatype data[maxn];
int length;
}
只读接口:索引
Datatype Seqlistindex(struct Seqlist *sq,int i){
return sq->data[i];
}
只读接口:查找
Datatype SwqlistFind(struct seqlist *sq,Datatype dt){
int i;
for(i=0;i<sq->length;i++){
if(sq->data[i]==dt){
return i;
}
}
return -1;
}
只读接口:获取长度
Datatype Seqlistgetlength(struct Seqlist *sq){
return sq->length;
}
可写接口:插入
int SeqListInsert(struct SeqList *sq, int k, DataType v){
int i;
if(sq->length==maxn){
return 0;
}
for(i=sq->length;i>k;i--){
sq-data[i]=sq->[i-1];
}
sq->data[k]=v;
sq->length++;
}
可写接口:删除
int SeqListDelete(struct SeqList *sq, int k) {
int i;
if(sq->length == 0) {
return 0;
}
for(i = k; i < sq->length - 1; ++i) {
sq->data[i] = sq->data[i+1];
}
sq->length --;
return 1;
}
1,线性枚举 :给定一个长度为n(1≤n≤10^5)的整型数组,求所有数组元素中的其中的最小值。遍历数组,进行条件判断,条件满足则执行逻辑。这里的条件就是 枚举到的数 是否小于 当前最小值,执行逻辑为 将 当前枚举到的数 赋值给 当前最小值;
int findMin(int *nums,int numsize){
int i,mins=100000;
for(i=0;i<numsize;i++){
if(nums[i]<mins){
mins=nums[i];
}
}
return mins;
}
2,给定一个n(n≤10^5)个元素的整型数组a_i,再给出m(m≤10^5)次询问,每次询问是一个区间[l,r],求h(l,r)=ak(k为1到r的和)。 第一个枚举,利用一个数组sum,存储前i个元素的和。 第二个枚举,读入 m 组数据 l,r,对每组数据,通过 O(1) 获取答案,即 sum_r - sum_{r-1}
int sum[maxn];
int *prefixmax(int *nums,int numsize,int m,int *l,int *r){
int i;
int *ret;
for(i=0;i<numsize;i++){
sum[i]=nums[i]
if(i){
sum[i]+=nums[i];
}
}
ret=(int *)malloc(sizeof(int)*m);
for(i=0;i<m;i++){
int leftsum=l[i]==0?0:l[i]-1;
int rightsum=r[i];
ret[i]=ret[leftsum]-ret[rightsum];
}
return ret;
}
双指针:给定一个长度为n(1≤n≤10^7)的字符串s,求一个最长的满足所有字符不重复的子串。 维护两个指针i和j,区间[i,j] 内的子串,应该时刻保持其中所有字符不重复,一旦发现重复字符,就需要自增 i(即执行 i=i+1);否则,执行j=j+1,直到j不能再增加为止。 过程中,记录合法情况下j−i+1 的最大值。
int getmaxlen(int n,char *str,int &l,int &r){
int ans=0,i=0,j=-1,len;
memset(h,0,sizeof(h));
while(j++<n-1){
++h[str[j]];
if(h[str[j]]>=2){
--h[str[i]];//表示重新计算,如果str[i]对于的哈希表不减一,会影响后面做出的判断,相当于字符串从i之后开始计算
i++;
}
}
len=j-i+1;
if(len>ans){
ans=len;l=i;r=j;
}
return ans;
}
二分枚举:给定一个 n(n≤10^6)个元素的有序整型数组和一个target 值,求在 O(log_2n)的时间内找到值为target的整型的数组下标,不存在则返回-1。
a)令初始情况下,数组下标从 0 开始,且数组长度为n,则定义一个区间,它的左端点是l=0,右端点是 r=n−1;
b)生成一个区间中点 mid=(l+r)/2,并且判断 mid 对应的数组元素和给定的目标值的大小关系,主要有三种:
b.1)目标值 等于 数组元素,直接返回 mid;
b.2)目标值 大于 数组元素,则代表目标值应该出现在区间 [mid+1,r],迭代左区间端点l=mid+1;
b.3)目标值 小于 数组元素,则代表目标值应该出现在区间 [l,mid−1],迭代右区间端点:r=mid−1;
c)如果这时候 l>r,则说明没有找到目标值,返回−1;否则,回到 b)继续迭代。
int search(int *nums,int target,int numsize){
int l=0,r=numsize-1;
while(l<r){
int mid=(r+l)>>1;
if(nums[mid]==target){
return mid;
}else if(nums[mid]>target){
r=mid+1;
}else if(nums[mid]<target){
l=mid-1
}
}
return -1;
}
插入排序: 给定一个 n 个元素的数组,数组下标从 0 开始,采用「 插入排序 」将数组按照 「升序」排列。
void insertsort(int *a,int n){
int x,i,j;
for(i=1;i<n;i++){
x=a[i];
for(j=i-1;j>=0;j--){
if(a[j]>=x){
a[j+1]=a[j];
}else{
break;
}
a[j+1]=x;
}
}
}
冒泡排序:给定一个 n 个元素的数组,数组下标从 0 开始,采用「 冒泡排序 」将数组按照 「升序」排列
void SelectionSort(int n, int *a) {
int i, j;
for(i = 0; i < n - 1; ++i) {
int min = i;
for(j = i+1; j < n; ++j) {
if(a[j] < a[min]) {
min = j;
}
}
Swap(&a[i], &a[min]);
}
}
选择排序:给定一个 n 个元素的数组,数组下标从 0 开始,采用「 选择排序 」将数组按照 「升序」排列。
void SelectionSort(int n, int *a) {
int i, j;
for(i = 0; i < n - 1; ++i) {
int min = i;
for(j = i+1; j < n; ++j) {
if(a[j] < a[min]) {
min = j;
}
}
Swap(&a[i], &a[min]);
}
}