给你两个只包含 1 到 9 之间数字的数组 nums1
和 nums2
,每个数组中的元素 互不相同 ,请你返回 最小 的数字,两个数组都 至少 包含这个数字的某个数位。
提示:
1 <= nums1.length, nums2.length <= 9
1 <= nums1[i], nums2[i] <= 9
【hash table】
int minNumber(int* nums1, int nums1Size, int* nums2, int nums2Size){
int n1=nums1Size,n2=nums2Size;
int hash[10]={0};
int min1=10,min2=10;
for(int i=0;i<n1;i++){
hash[nums1[i]]++;
min1=fmin(min1,nums1[i]);
}
for(int i=0;i<n2;i++){
hash[nums2[i]]++;
min2=fmin(min2,nums2[i]);
}
//找出现过2次的数字,以及两个arr中的最小数
int equal=0,min=10;
for(int i=1;i<10;i++){
if(hash[i]==2){
equal=1;
min=fmin(min,i);
}
}
//有出现过2次数字,直接返回最小数
if(equal) return min;
else{
if(min1>min2){
return min1+min2*10;
}
else{
return min2+min1*10;
}
}
}
给你一个有根节点 root
的二叉树,返回它 最深的叶节点的最近公共祖先 。
回想一下:
0
,如果某一节点的深度为 d
,那它的子节点的深度就是 d+1
A
是一组节点 S
的 最近公共祖先,S
中的每个节点都在以 A
为根节点的子树中,且 A
的深度达到此条件下可能的最大值。提示:
[1, 1000]
的范围内。0 <= Node.val <= 1000
【递归】
/**
* Definition for a binary tree node.
* struct TreeNode {
* int val;
* struct TreeNode *left;
* struct TreeNode *right;
* };
*/
int getDepth(struct TreeNode *root){
if(!root) return 0;
//如果root==null,则返回0层
return fmax(getDepth(root->left),getDepth(root->right))+1;
//递归返回左右子树,层数++
}
struct TreeNode* lcaDeepestLeaves(struct TreeNode* root){
struct TreeNode *res=root,*cur=root;
while(cur){ //当cur不为空时
int left=getDepth(cur->left);
int right=getDepth(cur->right);
//left为当前节点的左节点的层
//right为当前节点的右节点的层
//层:从叶子节点往上的层数
if(left==right){
//如果左节点的层==右节点的层,则左右为叶子
res=cur;
break;
}
else if(left>right){
//左更深
cur=cur->left;
}
else{
//右更深
cur=cur->right;
}
}
return res;
}
给你一个整数数组 ranks
,表示一些机械工的 能力值 。ranksi
是第 i
位机械工的能力值。能力值为 r
的机械工可以在 r * n2
分钟内修好 n
辆车。
同时给你一个整数 cars
,表示总共需要修理的汽车数目。
请你返回修理所有汽车 最少 需要多少时间。
**注意:**所有机械工可以同时修理汽车。
提示:
1 <= ranks.length <= 105
1 <= ranks[i] <= 100
1 <= cars <= 106
【二分法】
能力值为r的工人,最多可以修sqrt(t/r)个车
二分上界为:min(ranks) x cars x cars
即让能力最低的人修好所有车,消耗的时间
int check(long long n,int cars,int *ranks,int ranksSize){
long long sum=0;
for(int i=0;i<ranksSize;i++){
sum+=sqrt(n/ranks[i]);
}
return sum>=cars;
}
long long repairCars(int *ranks,int ranksSize,int cars){
long long left=1,right=ranks[0];
for(int i=0;i<ranksSize;i++){
right=fmin(ranks[i],right);
}
right=right*cars*cars-1;
while(left<=right){
long long mid=(left+right)/2;
if(check(mid,cars,ranks,ranksSize)){
right=mid-1;
}
else{
left=mid+1;
}
}
return left;
}
给你一个正整数 arrivalTime
表示列车正点到站的时间(单位:小时),另给你一个正整数 delayedTime
表示列车延误的小时数。
返回列车实际到站的时间。
注意,该问题中的时间采用 24 小时制。
提示:
1 <= arrivaltime < 24
1 <= delayedTime <= 24
【模拟】
int findDelayedArrivalTime(int arrivalTime, int delayedTime){
return (arrivalTime+delayedTime)%24;
}
你这个学期必须选修 numCourses
门课程,记为 0
到 numCourses - 1
。
在选修某些课程之前需要一些先修课程。 先修课程按数组 prerequisites
给出,其中 prerequisites[i] = [ai, bi]
,表示如果要学习课程 ai
则 必须 先学习课程 bi
。
[0, 1]
表示:想要学习课程 0
,你需要先完成课程 1
。请你判断是否可能完成所有课程的学习?如果可以,返回 true
;否则,返回 false
。
提示:
1 <= numCourses <= 2000
0 <= prerequisites.length <= 5000
prerequisites[i].length == 2
0 <= ai, bi < numCourses
prerequisites[i]
中的所有课程对 互不相同【拓扑】
题解:207. 课程表 - 力扣(LeetCode)
bool canFinish(int numCourses, int** prerequisites, int prerequisitesSize, int* prerequisitesColSize){
if(prerequisitesSize==0) return 1;
int *ans=malloc(sizeof(int)*numCourses);
for(int i=0;i<numCourses;i++){
ans[i]=0;
}
int res=0;
for(int i=0;i<prerequisitesSize;i++){
//update in-point of every point
ans[prerequisites[i][0]]++;
}
for(int i=0;i<numCourses;i++){
if(ans[i]==0){
//current course is done
res++;
if(res==numCourses){
//learned courses == total courses
return 1;
}
for(int j=0;j<prerequisitesSize;j++){
if(prerequisites[j][1]==i){
//must-learn course of [j] is learnt
ans[prerequisites[j][0]]--;
}
}
ans[i]--;
i=-1;
}
}
return 0;
}
现在你总共有 numCourses
门课需要选,记为 0
到 numCourses - 1
。给你一个数组 prerequisites
,其中 prerequisites[i] = [ai, bi]
,表示在选修课程 ai
前 必须 先选修 bi
。
0
,你需要先完成课程 1
,我们用一个匹配来表示:[0,1]
。返回你为了学完所有课程所安排的学习顺序。可能会有多个正确的顺序,你只要返回 任意一种 就可以了。如果不可能完成所有课程,返回 一个空数组 。
提示:
1 <= numCourses <= 2000
0 <= prerequisites.length <= numCourses * (numCourses - 1)
prerequisites[i].length == 2
0 <= ai, bi < numCourses
ai != bi
[ai, bi]
互不相同【拓扑】
/**
* Note: The returned array must be malloced, assume caller calls free().
*/
int* findOrder(int numCourses, int** prerequisites, int prerequisitesSize, int* prerequisitesColSize, int* returnSize){
int** edges = (int**)malloc(sizeof(int*) * numCourses);
for (int i = 0; i < numCourses; i++) {
edges[i] = (int*)malloc(0);
}
int edgeColSize[numCourses];
memset(edgeColSize, 0, sizeof(edgeColSize));
int indeg[numCourses];
memset(indeg, 0, sizeof(indeg));
for (int i = 0; i < prerequisitesSize; ++i) {
int a = prerequisites[i][1], b = prerequisites[i][0];
edgeColSize[a]++;
edges[a] = (int*)realloc(edges[a], sizeof(int) * edgeColSize[a]);
edges[a][edgeColSize[a] - 1] = b;
++indeg[b];
}
int q[numCourses];
int l = 0, r = -1;
for (int i = 0; i < numCourses; ++i) {
if (indeg[i] == 0) {
q[++r] = i;
}
}
int* result = (int*)malloc(sizeof(int) * numCourses);
int resultSize = 0;
int visited = 0;
while (l <= r) {
++visited;
int u = q[l++];
result[resultSize++] = u;
for (int i = 0; i < edgeColSize[u]; ++i) {
--indeg[edges[u][i]];
if (indeg[edges[u][i]] == 0) {
q[++r] = edges[u][i];
}
}
}
for (int i = 0; i < numCourses; i++) {
free(edges[i]);
}
free(edges);
if (visited == numCourses) {
*returnSize = numCourses;
} else {
*returnSize = 0;
}
return result;
}
这里有 n
门不同的在线课程,按从 1
到 n
编号。给你一个数组 courses
,其中 courses[i] = [durationi, lastDayi]
表示第 i
门课将会 持续 上 durationi
天课,并且必须在不晚于 lastDayi
的时候完成。
你的学期从第 1
天开始。且不能同时修读两门及两门以上的课程。
返回你最多可以修读的课程数目。
提示:
1 <= courses.length <= 104
1 <= durationi, lastDayi <= 104
【C++的优先队列】(不会orz)
class Solution {
public:
int scheduleCourse(vector<vector<int>>& courses) {
sort(courses.begin(), courses.end(), [](const auto& c0, const auto& c1) {
return c0[1] < c1[1];
});
priority_queue<int> q;
// 优先队列中所有课程的总时间
int total = 0;
for (const auto& course: courses) {
int ti = course[0], di = course[1];
if (total + ti <= di) {
total += ti;
q.push(ti);
}
else if (!q.empty() && q.top() > ti) {
total -= q.top() - ti;
q.pop();
q.push(ti);
}
}
return q.size();
}
};