给定三个链表,找出三个链表中所有的公共元素。
例子:
Input :
10 15 20 25 12
10 12 13 15
10 12 15 24 25 26
Output : 10 12 15
Input :
1 2 3 4 5
1 2 3 4 6 9 8
1 2 4 5 10
Output : 1 2 4
方法一:(简单)
使用三指针迭代给定的三个链表,如果有任何公共元素,则打印该元素。
上述解决方案的时间复杂度为 O(N*N*N)
方法二:(使用归并排序)
在这种方法中,我们首先对三个列表进行排序,然后遍历排序后的列表以获得交集。
以下是获得三个列表交集的步骤:
1) 使用归并排序对第一个链表进行排序。这一步需要 O(mLogm) 时间。有关此步骤的详细信息,请参阅此帖子。
2) 使用归并排序对第二个链表进行排序。这一步需要 O(nLogn) 时间。有关此步骤的详细信息,请参阅此帖子。
3) 使用归并排序对第三个链表进行排序。这一步需要 O(pLogp) 时间。有关此步骤的详细信息,请参阅此帖子。
3) 线性扫描三个排序列表得到交集。这一步需要 O(m + n + p) 时间。此步骤可以使用与此处讨论的排序数组算法相同的算法来实现。
该方法的时间复杂度为 O(mLogm + nLogn + plogp),优于方法 1 的时间复杂度。
方法3:(散列)
以下是使用散列获得三个列表交集的步骤:
1) 创建一个空的哈希表。遍历第一个链表并将哈希表中的所有元素频率标记为1。这一步需要 O(m) 时间。
2) 遍历第二个链表,如果哈希表中当前元素频率为1,则将其标记为2。这一步需要O(n)时间。
3) 迭代第三个链表,如果哈希表中当前元素频率为2,则标记为3。这一步需要O(p)时间。
4)现在再次迭代第一个链表以检查元素的频率。如果哈希表中存在频率为 3 的元素,则它将出现在三个链表的交集中。这一步需要 O(m) 时间。
该方法的时间复杂度为 O(m + n + p),优于方法 1 和方法 2 的时间复杂度。
下面是上述想法的实现。
C++
// C++ program to find common element
// in three unsorted linked list
#include
#define max 1000000
using namespace std;
/* Link list node */
struct Node {
int data;
struct Node* next;
};
/* A utility function to insert a node at the
beginning of a linked list */
void push(struct Node** head_ref, int new_data)
{
struct Node* new_node =
(struct Node *)malloc(sizeof(struct Node));
new_node->data = new_data;
new_node->next = (*head_ref);
(*head_ref) = new_node;
}
/* print the common element in between
given three linked list*/
void Common(struct Node* head1,
struct Node* head2, struct Node* head3)
{
// Creating empty hash table;
unordered_map hash;
struct Node* p = head1;
while (p != NULL) {
// set frequency by 1
hash[p->data] = 1;
p = p->next;
}
struct Node* q = head2;
while (q != NULL) {
// if the element is already exist in the
// linked list set its frequency 2
if (hash.find(q->data) != hash.end())
hash[q->data] = 2;
q = q->next;
}
struct Node* r = head3;
while (r != NULL) {
if (hash.find(r->data) != hash.end() &&
hash[r->data] == 2)
// if the element frquancy is 2 it means
// its present in both the first and second
// linked list set its frquancy 3
hash[r->data] = 3;
r = r->next;
}
for (auto x : hash) {
// if current frequency is 3 its means
// element is common in all the given
// linked list
if (x.second == 3)
cout << x.first << " ";
}
}
// Driver code
int main()
{
// first list
struct Node* head1 = NULL;
push(&head1, 20);
push(&head1, 5);
push(&head1, 15);
push(&head1, 10);
// second list
struct Node* head2 = NULL;
push(&head2, 10);
push(&head2, 20);
push(&head2, 15);
push(&head2, 8);
// third list
struct Node* head3 = NULL;
push(&head3, 10);
push(&head3, 2);
push(&head3, 15);
push(&head3, 20);
Common(head1, head2, head3);
return 0;
}
Java
// Java program to find common element
// in three unsorted linked list
import java.util.*;
class GFG
{
static int max = 1000000;
/* Link list node */
static class Node
{
int data;
Node next;
};
/* A utility function to insert a node
at the beginning of a linked list */
static Node push(Node head_ref,
int new_data)
{
Node new_node = new Node();
new_node.data = new_data;
new_node.next = head_ref;
head_ref = new_node;
return head_ref;
}
/* print the common element in between
given three linked list*/
static void Common(Node head1,
Node head2,
Node head3)
{
// Creating empty hash table;
HashMap hash = new HashMap();
Node p = head1;
while (p != null)
{
// set frequency by 1
hash. put(p.data, 1);
p = p.next;
}
Node q = head2;
while (q != null)
{
// if the element is already exist in the
// linked list set its frequency 2
if (hash.containsKey(q.data))
hash. put(q.data, 2);
q = q.next;
}
Node r = head3;
while (r != null)
{
if (hash.containsKey(r.data)&&
hash.get(r.data) == 2)
// if the element frquancy is 2 it means
// its present in both the first and second
// linked list set its frquancy 3
hash. put(r.data, 3);
r = r.next;
}
for (Map.Entry x : hash.entrySet())
{
// if current frequency is 3 its means
// element is common in all the given
// linked list
if (x.getValue() == 3)
System.out.println(x.getKey() + " ");
}
}
// Driver code
public static void main(String[] args)
{
// first list
Node head1 = null;
head1 = push(head1, 20);
head1 = push(head1, 5);
head1 = push(head1, 15);
head1 = push(head1, 10);
// second list
Node head2 = null;
head2 = push(head2, 10);
head2 = push(head2, 20);
head2 = push(head2, 15);
head2 = push(head2, 8);
// third list
Node head3 = null;
head3 = push(head3, 10);
head3 = push(head3, 2);
head3 = push(head3, 15);
head3 = push(head3, 20);
Common(head1, head2, head3);
}
}
// This code is contributed by 29AjayKumar
Python3
# Python3 program to find common element
# in three unsorted linked list
max = 1000000
# Link list node
class Node:
def __init__(self, data):
self.data = data
self.next = None
# A utility function to insert a node at the
# beginning of a linked list
def push( head_ref, new_data):
new_node = Node(new_data)
new_node.next = head_ref
head_ref = new_node
return head_ref
# Print the common element in between
# given three linked list
def Common(head1, head2, head3):
# Creating empty hash table;
hash = dict()
p = head1
while (p != None):
# Set frequency by 1
hash[p.data] = 1
p = p.next
q = head2
while (q != None):
# If the element is already exist in the
# linked list set its frequency 2
if (q.data in hash):
hash[q.data] = 2
q = q.next
r = head3
while (r != None):
if (r.data in hash) and hash[r.data] == 2:
# If the element frquancy is 2 it means
# its present in both the first and second
# linked list set its frquancy 3
hash[r.data] = 3
r = r.next
for x in hash.keys():
# If current frequency is 3 its means
# element is common in all the given
# linked list
if (hash[x] == 3):
print(x, end = ' ')
# Driver code
if __name__=='__main__':
# First list
head1 = None
head1 = push(head1, 20)
head1 = push(head1, 5)
head1 = push(head1, 15)
head1 = push(head1, 10)
# Second list
head2 = None
head2 = push(head2, 10)
head2 = push(head2, 20)
head2 = push(head2, 15)
head2 = push(head2, 8)
# Third list
head3 = None
head3 = push(head3, 10)
head3 = push(head3, 2)
head3 = push(head3, 15)
head3 = push(head3, 20)
Common(head1, head2, head3)
# This code is contributed by rutvik_56
C#
// C# program to find common element
// in three unsorted linked list
using System;
using System.Collections.Generic;
class GFG
{
static int max = 1000000;
/* Link list node */
public class Node
{
public int data;
public Node next;
};
/* A utility function to insert a node
at the beginning of a linked list */
static Node push(Node head_ref,
int new_data)
{
Node new_node = new Node();
new_node.data = new_data;
new_node.next = head_ref;
head_ref = new_node;
return head_ref;
}
/* print the common element in between
given three linked list*/
static void Common(Node head1,
Node head2,
Node head3)
{
// Creating empty hash table;
Dictionary hash = new Dictionary();
Node p = head1;
while (p != null)
{
// set frequency by 1
hash.Add(p.data, 1);
p = p.next;
}
Node q = head2;
while (q != null)
{
// if the element is already exist in the
// linked list set its frequency 2
if (hash.ContainsKey(q.data))
hash[q.data] = 2;
q = q.next;
}
Node r = head3;
while (r != null)
{
if (hash.ContainsKey(r.data)&&
hash[r.data] == 2)
// if the element frquancy is 2 it means
// its present in both the first and
// second linked list set its frquancy 3
hash[r.data] = 3;
r = r.next;
}
foreach(KeyValuePair x in hash)
{
// if current frequency is 3 its means
// element is common in all the given
// linked list
if (x.Value == 3)
Console.Write(x.Key + " ");
}
}
// Driver code
public static void Main(String[] args)
{
// first list
Node head1 = null;
head1 = push(head1, 20);
head1 = push(head1, 5);
head1 = push(head1, 15);
head1 = push(head1, 10);
// second list
Node head2 = null;
head2 = push(head2, 10);
head2 = push(head2, 20);
head2 = push(head2, 15);
head2 = push(head2, 8);
// third list
Node head3 = null;
head3 = push(head3, 10);
head3 = push(head3, 2);
head3 = push(head3, 15);
head3 = push(head3, 20);
Common(head1, head2, head3);
}
}
// This code is contributed by Princi Singh
Javascript
10 15 20
时间复杂度:O(m + n + p)
如果您希望与专家一起参加现场课程,请参阅DSA 现场工作专业课程和学生竞争性编程现场课程。