C/C++ 基础算法1

125 阅读3分钟

本文已参与「新人创作礼」活动,一起开启掘金创作之路。

C/C++ 基础算法1

链表中倒数第k个节点

  输入一个链表,输出该链表中倒数第k个节点。为了符合大多数人的习惯,本题从1开始计数,即链表的尾节点是倒数第1个节点。

  例如,一个链表有 6 个节点,从头节点开始,它们的值依次是 1、2、3、4、5、6。这个链表的倒数第 3 个节点是值为 4 的节点。

给定一个链表: 1->2->3->4->5, 和 k = 2.

返回链表 4->5.


/**
 * Definition for singly-linked list.
 * struct ListNode {
 *     int val;
 *     struct ListNode *next;
 * };
 */


struct ListNode* getKthFromEnd(struct ListNode* head, int k){
    
}

实现/思路

//方法一:
使用C语言,遍历一次记录当前有多少个节点n,在返回第n-k个节点为头节点的链表即可。

//方法二:
struct ListNode* getKthFromEnd(struct ListNode* head, int k) {
	vector<ListNode*> arr;
	ListNode* node = head;
	while (node != nullptr)
	{
		arr.push_back(node);
		node = node->next;
	}
	if (arr.size() == k)
		return head;
	node = arr[arr.size() - k - 1];
	ListNode* temp = node->next;
	node->next = nullptr;
	return temp;
}

顺时针打印矩阵

输入一个矩阵,按照从外向里以顺时针的顺序依次打印出每一个数字。

输入:matrix = [
    [1,2,3],
    [4,5,6],
    [7,8,9]]
输出:[1,2,3,6,9,8,7,4,5]


输入:matrix = [
    [1,2,3,4],
    [5,6,7,8],
    [9,10,11,12]]
输出:[1,2,3,4,8,12,11,10,9,5,6,7]
// matrix矩阵
// matrixW 宽
// matrixH 高
int* spiralOrder(int* matrix, int matrixW, int matrixH) {
   
}

实现/思路

enum Dir
{
	Up,
	Down,
	Right,
	Left
};

int* spiralOrder(int* matrix, int matrixW, int matrixH)
{
	int* arr = (int*)malloc(sizeof(int) * matrixH * matrixW);
	int len = 0;
	int size = matrixH * matrixW;
	enum Dir direction = Right;
	int index = 0;
	int xIndex = 0, yIndex = 0;
	while (1)
	{
		if (direction == Right)
		{
			arr[len++] = matrix[index];
			if (index + 1 == matrixW)
				direction = Down;
			else index++;
		}
		else if (direction == Down)
		{
			index += matrixW;
			arr[len++] = matrix[index];
			if (index == matrixH * matrixW - 1)
			{
				direction = Left;
				--index;
			}
		}
		else if (direction == Left)
		{
			arr[len++] = matrix[index];
			if (index == matrixH * matrixW - matrixW + xIndex)
				direction = Up;
			else index--;
		}
		else if (direction == Up)
		{
			index -= matrixW;
			arr[len++] = matrix[index];
			if (index == matrixW + yIndex)
			{
				direction = Right;
				//此时已经遍历了一圈
				xIndex++;
				yIndex++;
				matrixH--;
				matrixW--;
				index++;
			}
		}

		if (len == size)
			break;
	}
	return arr;
}

第一个只出现一次的字符

在字符串 s 中找出第一个只出现一次的字符。如果没有,返回一个单空格。 s 只包含小写字母。

输入:s = "abaccdeff"
输出:'b'

输入:s = "" 
输出:' '

char firstUniqChar(char* s){

}

实现/思路

char firstUniqChar(char* s)
{
	int visited[26] = { 0 };
	char* start = s;
	while (*start != '\0')
	{
		visited[*start - 97] += 1;
		start++;
	}
	start = s;
	while (*start != '\0')
	{
		if (visited[*start - 97] == 1)
			return *start;
		start++;
	}
	return ' ';
}

不用加减乘除做加法

写一个函数,求两个整数之和,要求在函数体内不得使用 “+”、“-”、“*”、“/” 四则运算符号。

输入: a = 1, b = 1
输出: 2

int add(int a, int b){

}

实现/思路

我们可以将其想象为两个数的二进制相加,那么关键就在于如果两个数相同的位都为1,那么是应该进位的(即当前位为0,往前一位进1),我们可以使用位运算符将进位(都为1)和不需要进位(一个为0,一个为1)的操作相分离。通过两个数(转化为二进制观察)异或(^)操作,可以取出所有不需要进位的位,然后对于不需要进位的数,只需要直接转为相应十进制就可(即因为不需要进位,所以两个数异或,就是两数相加)。而对于需要进位的数,我们使用让两数按位与(&)操作,然后左移运算(<<)1,那么得到的结果就是相应需要进位的数,然后将进位的数加入相应加入累加到上一次的计算结果,重复上述操作,直至进位为0。

int add(int a, int b)
{
	int sum = a ^ b;
	int addNum = (a & b) << 1;
	while (addNum != 0)
	{
		int temp = sum;
		sum = sum ^ addNum;
		addNum = (temp & addNum) << 1;
	}
	return sum;
}

版权声明:本文为CSDN博主「ufgnix0802」的原创文章:
原文链接:blog.csdn.net/qq135595696…