剑指 offer:两个链表的第一个公共节点、数字在排序数组中的个数、二叉树的深度

本文深入探讨了链表与二叉树的算法实现,包括寻找两个链表的第一个公共节点,使用二分法统计排序数组中数字的出现次数,以及计算二叉树的深度。提供了详细的代码示例与分析。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

两个链表的第一个公共节点

题目描述
输入两个链表,找出它们的第一个公共结点。

分析
首先要明白公共节点的含义:即两个链表从某个节点开始重合,重合的第一个节点即为第一个公共节点。
那么最直接的想法就是从后往前推,找到第一个不相同的节点,它的 next 即为我们想要的公共节点。
这种方法要用栈。可以从前往后吗?其实也是可以的,先求出两个链表的长度 len1,len2,然后对较长的那个链表,先遍历 | len2-len1 | 次,知道两个链表长度相等,然后就可以对两个链表同时遍历了。
代码如下:

ListNode* FindFirstCommonNode(ListNode* pHead1, ListNode* pHead2) {
	if (pHead1 == NULL || pHead2 == NULL) {
		return NULL;
	}
	int len1 = 0, len2 = 0;
	ListNode *p = pHead1;
	while (p) {
		++len1;
		p = p->next;
	}
	ListNode* p2 = pHead2;
	while (p2) {
		++len2;
		p2 = p2->next;
	}
	if (len1 >= len2) {
		p = pHead1;
		p2 = pHead2;
	}
	else if(len1 <len2){
		p = pHead2;
		p2 = pHead1;
	}
	// p 指向较长的链表
	for (int i = 0; i <= abs(len2 - len1); ++i) {
		p = p->next;
	}
	while (p != p2) {
		p = p->next;
		p2 = p2->next;
	}
	return p;
}

数字在排序数组中的个数

题目描述
统计一个数字在排序数组中出现的次数。
分析:这题当然是很简单了,但我想用二分法做,因为自己的代码能力比较差,虽然二分法也不难,但做起来可能就有各种各样的作物。事实证明我确实做了蛮久的。惭愧。
直接贴代码吧:

int GetNumberOfK(vector<int> data, int k) {
	if (data.size() == 0) {
		return 0;
	}
	int r = data.size() - 1;
	int p = 0;
	int q = (p + r) / 2;
	while (p < r && data[q] != k) {
		if (data[q] > k) {
			r = q - 1;
			q = (p + r) / 2;
		 }
		else if (data[q] < k) {
			p = q + 1;
			q = (p + r) / 2;
		}
	}
	if (p == q) {
		if (data[q] == k) {
			return 1;
		}
		return 0;
	}
	int count = 0;
	int i = q, j = q + 1;
	while (i >= p && data[i] == k) {
		++count;
		--i;
	}
	while (j <= r && data[j] == k) {
		++count;
		++j;
	}
	return count;
}

二叉树的深度

分析:深度优先遍历即可。

void deepFirst(TreeNode* pRoot, int count, int &mLen) {
	if (!pRoot->left && !pRoot->right) {
		if (mLen < count) {
			mLen = count;
		}
		return;
	}
	if (pRoot->left) {
		deepFirst(pRoot->left, count + 1, mLen);
	}
	if (pRoot->right) {
		deepFirst(pRoot->right, count + 1, mLen);
	}
}

int TreeDepth(TreeNode* pRoot)
{
	if (!pRoot) {
		return 0;
	}
	int count = 1;
	int mLen = 0;
	deepFirst(pRoot, count, mLen);
	return mLen;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值