C语言leetcode(二)

文章目录

    • [C语言][LeetCode][169] Majority Element
    • [C语言][LeetCode][189] Rotate Array
    • [C语言][LeetCode][206] Reverse Linked List
    • [C语言][LeetCode][217] Contains Duplicate
    • [C语言][LeetCode][219] Contains Duplicate II
    • [C语言][LeetCode][234] Palindrome Linked List
    • [C语言][LeetCode][237] Delete Node in a Linked List
    • [C语言][LeetCode][268] Missing Number
    • [C语言][LeetCode][283]Move Zeroes
    • [C语言][LeetCode][344] Reverse String
    • [C语言][LeetCode][345] Reverse Vowels of a String
    • [C语言][LeetCode][383] Ransom Note
    • [C语言][LeetCode][387] First Unique Character in a String
    • [C语言][LeetCode][485] Max Consecutive Ones
    • [C语言][LeetCode][551] Student Attendance Record I
    • [C语言][LeetCode][561] Array Partition I
    • [C语言][LeetCode][657] Judge Route Circle

[C语言][LeetCode][169] Majority Element

题目链接:https://leetcode.com/problems/majority-element/description/

题目意思是给定一个数组,找出一个出现次数大于n/2的数,题目假设一定有这个数且数组非空。

//解题思路:做减法操作,即比较两个数,不相同,就忽略,相同,则计数,那么最后剩下来的那个,就是你要的数。

#include 
int majorityElement(int* nums, int numsSize)
{
int i, num;
int count = 0;

for (i = 0; i

[C语言][LeetCode][189] Rotate Array

题目链接:https://leetcode.com/problems/rotate-array/description/

题目意思是给定一个整形数组,传入一个k参数,另其旋转k次,有点类似队列的感觉,从队头出去K个,然后按照顺序再插入到队尾。

//解题思路:
//仔细观察题目给的例子,可以看出
//| —— - | 开始位置 | 现在位置 |
//| 数字7 | —–7—– | —–3—– |
//| 数字6 | —–6—– | —–2—– |
//| 数字5 | —–5—– | —–1—– |
//从上面关系,可以看出cur_location = origin_location + k - array_size
//因为超出了array_size之后,会重新从队头插入,所以上面的等式变成如下关系
//cur_location = (origin_location + k )% array_size

#include 
void rotate(int* nums, int numsSize, int k) {
int i = 0;
int *array = (int *)malloc(sizeof(int)*numsSize);

for (i = 0; i

[C语言][LeetCode][206] Reverse Linked List

题目链接:https://leetcode.com/problems/reverse-linked-list/description/

//题目意思是将给定链表反转

//解题思路:

如下图给定一个存放5个数的链表。

在这里插入图片描述

???

首先对于链表设置两个指针:
C语言leetcode(二)_第1张图片
然后依次将旧链表上每一项添加在新链表的后面,然后新链表的头指针NewH移向新的链表头,如下图所示。此处需要注意,不可以上来立即将上图中P->next直接指向NewH,这样存放2的地址就会被丢弃,后续链表保存的数据也随之无法访问。而是应该设置一个临时指针tmp,先暂时指向P->next指向的地址空间,保存原链表后续数据。然后再让P->next指向NewH,最后P=tmp就可以取回原链表的数据了,所有循环访问也可以继续展开下去。
C语言leetcode(二)_第2张图片
指针继续向后移动,直到P指针指向NULL停止迭代。
C语言leetcode(二)_第3张图片
最后一步:
C语言leetcode(二)_第4张图片

#include 

struct ListNode
{
int val;
struct ListNode *next;
};

struct ListNode* reverseList(struct ListNode* head) {
if (NULL == head) {
return head;
}

struct ListNode* p = head, *newH = NULL;
while (p != NULL) //一直迭代到链尾
{
struct ListNode* tmp = p->next; //暂存p下一个地址,防止变化指针指向后找不到后续的数
p->next = newH; //p->next指向前一个空间
newH = p; //新链表的头移动到p,扩长一步链表
p = tmp; //p指向原始链表p指向的下一个空间
}
return newH;
}


int main()
{
struct ListNode a, b, c;
a.val = 1;
b.val = 3;
c.val = 2;
a.next = &b;
b.next = &c;
c.next = NULL;
struct ListNode *head;
head = &a;
//打印原链表
struct ListNode *q = head;
do
{
printf("%d ", q->val);
q = q->next;
} while (q != NULL);

printf("\n");
struct ListNode*p = reverseList(head);
//打印反转后的链表
do
{
printf("%d ",p->val);
p = p->next;
} while (p != NULL);
return 0;
}

[C语言][LeetCode][217] Contains Duplicate

题目链接:https://leetcode.com/problems/contains-duplicate/description/

题目意思是如果整形数组里有相同的整形就返回true,否则返回false。

//解题思路:用两个嵌套循环比较是否存在相同的整形。

#include 
#include 
bool containsDuplicate(int* nums, int numsSize)
{
int i = 0, j = 0;
for (i = 0; i

[C语言][LeetCode][219] Contains Duplicate II

题目链接:https://leetcode.com/problems/contains-duplicate-ii/description/

题目意思是给定一个整型数组,找出两个相等的数(nums[i] = nums[j]),并且i和j之间的差要小于等于k。
//解题思路:我这里用的比较笨的方法,用双重循环去查找。

#include 
#include 
bool containsNearbyDuplicate(int* nums, int numsSize, int k) {
int i = 0, j = 0;
bool flag = false;

for (i = 0; i

[C语言][LeetCode][234] Palindrome Linked List

题目要求是判断一个链表是否是回文链表
//解题思路:首先找到链表的中点,可以使用快慢指针来实现
//每次快指针走两步,慢指针走一步,等快指针走完时,慢指针的位置就是中点
//另外结合206题,首先将后半段链表反转,与前半段链表进行比较即可

#include 
#include 
struct ListNode
{
int val;
struct ListNode *next;
};
struct ListNode* reverseList(struct ListNode* head) {
if (NULL == head) {
return head;
}
struct ListNode* p = head, *newH = NULL;
while (p != NULL) //一直迭代到链尾
{
struct ListNode* tmp = p->next; //暂存p下一个地址,防止变化指针指向后找不到后续的数
p->next = newH; //p->next指向前一个空间
newH = p; //新链表的头移动到p,扩长一步链表
p = tmp; //p指向原始链表p指向的下一个空间
}
return newH;
}
bool isPalindrome(struct ListNode* head) 
{
struct ListNode* fast = head;
struct ListNode* slow = head;
while (fast != NULL && fast->next != NULL) 
{
slow = slow->next;
fast = fast->next->next;
}
///reverse the bottom half list
struct ListNode* rHead = reverseList(slow);
while (head != NULL && rHead != NULL) 
{
if (head->val != rHead->val)
return false;
head = head->next;
rHead = rHead->next;
}
return true;
}
int main()
{
struct ListNode a, b, c, d;
a.val = 1;
b.val = 2;
c.val = 2;
d.val = 1;
a.next = &b;
b.next = &c;
c.next = &d;
d.next = NULL;
struct ListNode *head;
head = &a;
bool result = isPalindrome(head);
printf("%d",result);
return 0;
}

[C语言][LeetCode][237] Delete Node in a Linked List

题目意思是删除链表中的给定节点

//解题思路:删除给定节点的下一个节点,而将下个节点的信息保存在给定节点中。

#include 
struct ListNode
{
int val;
struct ListNode *next;
};
void deleteNode(struct ListNode* node) 
{
node->val = node->next->val;
node->next = node->next->next;
}

int main()
{
struct ListNode a, b, c, d;
a.val = 1;
b.val = 2;
c.val = 3;
d.val = 4;
a.next = &b;
b.next = &c;
c.next = &d;
d.next = NULL;

struct ListNode *p = &a;
do
{
printf("%d",p->val);
p = p->next;
} while (p!=NULL);
struct ListNode *node = &a;
deleteNode(node);
printf("\n");
p = &a;
do
{
printf("%d", p->val);
p = p->next;
} while (p != NULL);

return 0;
}


[C语言][LeetCode][268] Missing Number

题目链接:https://leetcode.com/problems/missing-number/description/

//解题思路:对于0-n个数,它们的和sum是确定的,那么用sum减去给定n个数的和就求出了missing的那个数
//思路很巧妙!!!

#include 
int missingNumber(int* nums, int numsSize) {
int expectedSum = (1 + numsSize)*numsSize / 2;
int i = 0;
int sum = 0;
for (i = 0; i < numsSize; i++) {
sum += nums[i];
}
return expectedSum - sum;
}

int main() {
int nums[] = { 0, 1, 2 , 4};
int numsSize = sizeof(nums) / sizeof(nums[0]);
int val = missingNumber(nums,numsSize);
printf("%d",val);
return 0;
}

[C语言][LeetCode][283]Move Zeroes

题目链接:https://leetcode.com/problems/move-zeroes/description/

题目意思是将一个数组里面的0全部往后放。

//解题思路:利用双指针,i指向0的元素,j指向非0的元素,从头开始遍历,
//如果遇到i和j的位置不相等,则交换i和j的内容,并将j的内容置为0。

#include 
void moveZeroes(int* nums, int numsSize)
{
int i = 0, j = 0;

while (j

[C语言][LeetCode][344] Reverse String

题目链接:https://leetcode.com/problems/reverse-string/description/

题目意思是返回所给字符串的逆序字符串。

//解题思路:直接逆序复制字符串,然后返回复制的逆序字符串。

#include 

char* reverseString(char* s) 
{
int len = strlen(s), i = 0;
char *temp;
temp = (char *)malloc(len + 1);
while (s[i] != '\0')
{
temp[i] = s[len - i - 1];
i++;
}
temp[len] = '\0';
return temp;
}

int main()
{
char s[] = "hello";
char *temp = reverseString(s);
int len = strlen(s);

for (int i = 0; i < len; i++)
{
printf("%c",temp[i]);
}


printf("\n");
printf("%s\n", temp);
return 0;
}

[C语言][LeetCode][345] Reverse Vowels of a String

题目链接:https://leetcode.com/problems/reverse-vowels-of-a-string/description/

//题目要求是将所给字符串中的元音字母逆序排列,辅音字母不变,然后输出变换后的字符串。
//元音字母共5个(‘a’, ‘e’, ‘i’, ‘o’, ‘u’),其余均为辅音字母。

//解题思路:双指针,一个left从头部开始找,另一个right从尾部开始找,
//若left及right均为元音,交换二者。截止条件为left >= right。

#include 

int isVowelsChar(char p) 
{
return (p == 'a' || p == 'e' || p == 'i' || p == 'o' || p == 'u' || p == 'A' || p == 'E' || p == 'I' || p == 'O' || p == 'U');
}
char* reverseVowels(char* s) {
int left = 0;
int right = strlen(s) - 1;
if (strlen(s) < 1) {
return s;
}
while (left < right) 
{
while (!isVowelsChar(s[left]) && left < right) 
{
left++;
}
while (!isVowelsChar(s[right]) && left < right) 
{
right--;
}
char temp = s[left];
s[left] = s[right];
s[right] = temp;
left++;
right--;
}
return s;
}

int main()
{
char s[] = "leetcode";
char *p = reverseVowels(s);
for(int i = 0; i < strlen(p);i++)
{
printf("%c",p[i]);
}
return 0;
}

[C语言][LeetCode][383] Ransom Note

题目链接:https://leetcode.com/problems/ransom-note/description/

题目意思是对比两个字符串ransomNote和magazine,
//如果ransomNote中的字符均可从magazine中找到,并且对应的字符个数不小于magazine,则返回true,否则false。

/*解题思路:
本题需要满足两个条件:
(1)magazine需要包含ransomNot中所有的字符。
(2)magazine所包含的ransomNot字符相对应的数量不小于ransomNot。

首先从ransomNot中的首个字符开始,与magazine中的字符逐个比较,若找到第一相同的,
则将magazine中的这个相同的字符替换为除小写字母外的其他字符(题目中所有字符均只有小写字母),
然后将ransomNot中的下一个字符与magazine比较,找到相同的就替换,依次完成ransomNot中所有字符的比较查找,
如果某个字符没有在magazine中找到,则结束比较,返回false。
需要注意的是,当ransomNot为空时,需返回true。若magazine为空,而ransomNot不为空,则返回false。
*/

#include 
#include 
#include 
#include  //bool类型

bool canConstruct(char* ransomNote, char* magazine)
{
int i = 0, j = 0;
bool flag = true;
int size1 = strlen(ransomNote);
int size2 = strlen(magazine);
if (size1 == 0) //ransomNot为空
return true;
if (size1 != 0 && size2 == 0) //magazine为空
return false;

for (i = 0; i

[C语言][LeetCode][387] First Unique Character in a String

题目链接:https://leetcode.com/problems/first-unique-character-in-a-string/description/

题目要求:找到一个字符串中第一个不重复的字符,假设字符串中的所有字符均为小写字母。

//解题思路:由于字符串中的字符全部为小写字母,故用一个大小为26的数组来存储每个字母出现的次数。
//然后在从字符串中的第一个字符开始依次判断其出现次数是否为1。

#include 

int firstUniqChar(char* s) 
{
int i = 0, j = 0;
int len = strlen(s);
int freq[26];

for (i = 0; i<26; i++) 
{
freq[i] = 0;
}

for (i = 0; i

[C语言][LeetCode][485] Max Consecutive Ones

题目链接:https://leetcode.com/problems/max-consecutive-ones/description/

//解题思路:两个临时变量就可以了,一个记录每次连续的值的大小,一个记录最大的连续值的大小

#include 
int findMaxConsecutiveOnes(int* nums, int numsSize)
{
int i = 0, max = 0, sum = 0;
for (i = 0; imax)
{
max = sum;
}
}
return max;
}

int main()
{
int nums[] = {1,0,0,1,1,1,1,1};
int numsSize = sizeof(nums) / sizeof(nums[0]);
printf("%d\n",findMaxConsecutiveOnes(nums,numsSize));
return 0;
}

[C语言][LeetCode][551] Student Attendance Record I

题目链接:https://leetcode.com/problems/student-attendance-record-i/description/

//题目意思是根据学生的出勤登记情况判定其是否可以得奖,已知A代表缺席,L代表迟到。
//若连续迟到三次及三次以上或缺席一次以上就不能得奖。

#include 
#include 

bool checkRecord(char* s) {
int len = strlen(s);
int record = 0;
int i = 0;
bool flag = true;

for (i = 0; i1)
flag = false;
return flag;
}

int main()
{
char s[] = "PPALLL";
bool result = checkRecord(s);
printf("%d",result);
return 0;
}

[C语言][LeetCode][561] Array Partition I

题目链接:https://leetcode.com/problems/array-partition-i/description/

//题目意思是在2n长度的数组中,两两一组,将每组中较小的数累加起来,求一个最大值

//解题思路是对数组先排序,然后取所有的arr[2n]相加即可。

#include 
void my_qsort(int* nums, int l, int r)//快速排序算法
{
if (l*(nums + l))//若比关键值大,则把该值放到右端点(交换该值与右端点值)
{
int temp = *(nums + j);
*(nums + j) = *(nums + i);
*(nums + i) = temp;
j--;//右端点右移
}
else//否则就选择下一个继续比较
{
i++;
}
}
if (*(nums + i) >= *(nums + l))
{
i--;
}
int temp = *(nums + i);
*(nums + i) = *(nums + l);
*(nums + l) = temp;
my_qsort(nums, l, i - 1);//递归调用
my_qsort(nums, i + 1, r);
}
}
int arrayPairSum(int* nums, int numsSize) {
my_qsort(nums, 0, numsSize - 1);
int sum = 0;
for (int i = 0; i

[C语言][LeetCode][657] Judge Route Circle

题目链接:https://leetcode.com/problems/judge-route-circle/description/

//题目意思是给出几个字母,分别用UDLR来表示上下左右,最后看是否走回原处。

//解题思路是定义两个变量,LR、UD分别来表示左右方向和上下方向上的位移量,如果两个位移量都是零,则返回true,否则返回false。

#include 
#include 
bool judgeCircle(char* moves) {
int LR = 0, UD = 0;//左右上下移动位数,负数为左、下,正数则反之 
int i = 0;
int len = strlen(moves);
for (i = 0; i

你可能感兴趣的:(C语言,leetcode)