1.两个链表第一个公共子节点
方法 1:暴力
暴力法遍历第一个链表的每个节点,对每个节点检查第二个链表,找到共同节点。复杂度为 O(m*n)。
import java.util.*;
/*
public class ListNode {
int val;
ListNode next = null;
ListNode(int val) {
this.val = val;
}
}*/
public class Solution {
public ListNode FindFirstCommonNode(ListNode pHead1, ListNode pHead2) {
ListNode head1 = pHead1;
while(head1!=null){
ListNode head2 = pHead2;
while(head2!=null){
if(head1.equals(head2)){
return head2;
}else{
head2 = head2.next;
}
}
head1 = head1.next;
}
return head1;
}
}
方法2:栈
使用两个栈分别存储两链表节点,从尾部开始比较,直至找到最后一个共同节点。时间复杂度为 O(m + n)。
public class Solution {
public ListNode FindFirstCommonNode(ListNode pHead1, ListNode pHead2) {
Stack<ListNode> stack1 = new Stack<>();
Stack<ListNode> stack2 = new Stack<>();
// 将第一个链表的所有节点压入栈1
while (pHead1 != null) {
stack1.push(pHead1);
pHead1 = pHead1.next;
}
// 将第二个链表的所有节点压入栈2
while (pHead2 != null) {
stack2.push(pHead2);
pHead2 = pHead2.next;
}
ListNode lastCommon = null;
// 比较两个栈的栈顶元素
while (!stack1.isEmpty() && !stack2.isEmpty()) {
if (stack1.peek() == stack2.peek()) {
lastCommon = stack1.peek();
stack1.pop();
stack2.pop();
} else {
break;
}
}
return lastCommon; // 返回最后一个共同节点
}
}
方法3:用HashMap
public class Solution {
public ListNode FindFirstCommonNode(ListNode pHead1, ListNode pHead2) {
HashMap<ListNode, Boolean> map = new HashMap<>();
// 将第一个链表的节点存储在HashMap中
ListNode current = pHead1;
while (current != null) {
map.put(current, true);
current = current.next;
}
// 检查第二个链表的节点是否存在于HashMap中
current = pHead2;
while (current != null) {
if (map.containsKey(current)) {
return current; // 找到第一个公共子节点
}
current = current.next;
}
return current; // 没有公共子节点
}
}
方法4:用HashSet
public class Solution {
public ListNode findFirstCommonNodeBySet(ListNode headA, ListNode headB) {
Set<ListNode> set = new HashSet<>();
while (headA != null) {
set.add(headA);
headA = headA.next;
}
while (headB != null) {
if (set.contains(headB)) {
return headB;
}
headB = headB.next;
}
return null;
}
}
2.判断是否为回文字符串
方法1: 数组 for-loop
public class Solution {
/**
* 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可
*
*
* @param str string字符串 待判断的字符串
* @return bool布尔型
*/
public boolean judge (String str) {
char[] chars = str.toCharArray();
int maxSize = chars.length / 2;
for (int i = 0; i < maxSize; i++) {
if (chars[i] != chars[chars.length - 1 - i]) {
return false;
}
}
return true;
}
}
public class Solution {
/**
* 代码中的类名、方法名、参数名已经指定,请勿修改,直接返回方法规定的值即可
*
*
* @param ListNode head
* @return bool布尔型
*/
public boolean judge (ListNode head) {
if (head == null) {
return true; // 空链表默认为回文
}
// 计算链表长度
int length = 0;
ListNode temp = head;
while (temp != null) {
length++;
temp = temp.next;
}
// 初始化数组并填充链表的值
int[] values = new int[length];
temp = head;
int index = 0;
while (temp != null) {
values[index++] = temp.val;
temp = temp.next;
}
// 判断是否回文
int halfLength = length / 2;
for (int i = 0; i < halfLength; i++) {
if (values[i] != values[length - 1 - i]) {
return false;
}
}
return true;
}
}
方法1.1 ArrayList(动态长度变化)
import java.util.ArrayList;
public boolean judge(ListNode head) {
ArrayList<Integer> list = new ArrayList<>();
ListNode temp = head;
while(temp != null) {
list.add(temp.val);
temp = temp.next;
}
int maxSize = list.size() / 2;
for (int i = 0; i < maxSize; i++) {
if (!list.get(i).equals(list.get(list.size() - 1 - i))) {
return false;
}
}
return true;
}
方法2.0:全压栈,全比完
public boolean isPalindrome(ListNode head) {
ListNode temp = head;
Stack<Integer> stack = new Stack<>();
// 把链表节点的值压入栈中
while (temp != null) {
stack.push(temp.val);
temp = temp.next;
}
// 之后一边出栈,一边比较
while (head != null) {
if (head.val != stack.pop()) {
return false;
}
head = head.next;
}
return true;
}