Given an array of strings arr[] representing votes cast in an election, where each string is the name of a candidate in lowercase English letters. Find the candidate who received the maximum number of votes.
If multiple candidates receive the same highest number of votes, return the lexicographically smaller candidate name along with its vote count.
Examples:
Input: arr[] = ["john", "johnny", "jackie", "johnny", "john", "jackie", "jamie", "jamie", "john", "johnny", "jamie", "johnny", "john"]
Output: ["john", "4"]
Explanation: The candidates in the election are john, johnny, jackie, and jamie. Both john and johnny receive 4 votes each, while jackie and jamie receive 2 and 3 votes, respectively. Since john and johnny have the same highest number of votes, we return john because it is lexicographically smaller. Hence, the output is ["john", "4"].Input: arr[] = ["virat", "rohit", "rishabh", "rohit", "virat", "rohit"]
Output: ["rohit", "3"]
Explanation: There are three candidates in the election: virat, rohit, and rishabh. Among them, virat receives 2 votes, rohit receives 3 votes, and rishabh receives 1 vote. Since rohit has the highest number of votes, the output is ["rohit", "3"].
Table of Content
[Naive Approach] Using Two Nested Loops - O(n ^ 2) Time and O(1) Space
The idea is to find the winner is to consider each candidate one by one and count how many times their name appears in the entire array. While counting, keep track of the candidate with the highest number of votes. If two candidates have the same vote count, choose the one whose name is lexicographically smaller.
- Initialize maxVotes as 0 and winner as an empty string.
- Traverse each candidate in the array.
- For the current candidate, count its total occurrences by scanning the entire array.
- If the current count is greater than maxVotes, update maxVotes and winner.
- If the current count equals maxVotes, update winner only if the current candidate is lexicographically smaller.
- Return the winner along with maxVotes.
#include <bits/stdc++.h>
using namespace std;
// Function to find the candidate with the maximum votes
vector<string> winner(vector<string> &arr)
{
int n = arr.size();
string ans = "";
int maxVotes = 0;
// Check every candidate
for (int i = 0; i < n; i++)
{
// Count votes for the current candidate
int count = 0;
for (int j = 0; j < n; j++)
{
if (arr[i] == arr[j])
count++;
}
// Update winner if current candidate has more votes
if (count > maxVotes)
{
maxVotes = count;
ans = arr[i];
}
// If votes are equal, choose the lexicographically smaller name
else if (count == maxVotes && arr[i] < ans)
{
ans = arr[i];
}
}
return {ans, to_string(maxVotes)};
}
// Driver code
int main()
{
vector<string> arr = {"john", "johnny", "jackie", "johnny", "john", "jackie", "jamie",
"jamie", "john", "johnny", "jamie", "johnny", "john"};
vector<string> ans = winner(arr);
cout << ans[0] << " " << ans[1] << endl;
return 0;
}
import java.util.*;
class GFG {
// Function to find the candidate with the maximum votes
static ArrayList<String> winner(String[] arr)
{
int n = arr.length;
String ans = "";
int maxVotes = 0;
// Check every candidate
for (int i = 0; i < n; i++) {
// Count votes for the current candidate
int count = 0;
for (int j = 0; j < n; j++) {
if (arr[i].equals(arr[j]))
count++;
}
// Update winner if current candidate has more
// votes
if (count > maxVotes) {
maxVotes = count;
ans = arr[i];
}
// If votes are equal, choose the
// lexicographically smaller name
else if (count == maxVotes
&& arr[i].compareTo(ans) < 0) {
ans = arr[i];
}
}
ArrayList<String> result = new ArrayList<>();
result.add(ans);
result.add(String.valueOf(maxVotes));
return result;
}
// Driver code
public static void main(String[] args)
{
String[] arr
= { "john", "johnny", "jackie", "johnny",
"john", "jackie", "jamie", "jamie",
"john", "johnny", "jamie", "johnny",
"john" };
ArrayList<String> ans = winner(arr);
System.out.println(ans.get(0) + " " + ans.get(1));
}
}
# Function to find the candidate with the maximum votes
def winner(arr):
n = len(arr)
ans = ""
maxVotes = 0
# Check every candidate
for i in range(n):
# Count votes for the current candidate
count = 0
for j in range(n):
if arr[i] == arr[j]:
count += 1
# Update winner if current candidate has more votes
if count > maxVotes:
maxVotes = count
ans = arr[i]
# If votes are equal, choose the lexicographically smaller name
elif count == maxVotes and arr[i] < ans:
ans = arr[i]
return [ans, str(maxVotes)]
# Driver code
if __name__ == "__main__":
arr = [
"john", "johnny", "jackie", "johnny",
"john", "jackie", "jamie", "jamie",
"john", "johnny", "jamie", "johnny",
"john"
]
ans = winner(arr)
print(ans[0], ans[1])
using System;
using System.Collections.Generic;
class GFG {
// Function to find the candidate with the maximum votes
static List<string> winner(List<string> arr)
{
int n = arr.Count;
string ans = "";
int maxVotes = 0;
// Check every candidate
for (int i = 0; i < n; i++) {
// Count votes for the current candidate
int count = 0;
for (int j = 0; j < n; j++) {
if (arr[i] == arr[j])
count++;
}
// Update winner if current candidate has more
// votes
if (count > maxVotes) {
maxVotes = count;
ans = arr[i];
}
// If votes are equal, choose the
// lexicographically smaller name
else if (count == maxVotes
&& string.Compare(arr[i], ans) < 0) {
ans = arr[i];
}
}
return new List<string>{ ans, maxVotes.ToString() };
}
// Driver code
static void Main()
{
List<string> arr = new List<string>{
"john", "johnny", "jackie", "johnny",
"john", "jackie", "jamie", "jamie",
"john", "johnny", "jamie", "johnny",
"john"
};
List<string> ans = winner(arr);
Console.WriteLine(ans[0] + " " + ans[1]);
}
}
// Function to find the candidate with the maximum votes
function winner(arr)
{
const n = arr.length;
let ans = "";
let maxVotes = 0;
// Check every candidate
for (let i = 0; i < n; i++) {
// Count votes for the current candidate
let count = 0;
for (let j = 0; j < n; j++) {
if (arr[i] === arr[j])
count++;
}
// Update winner if current candidate has more votes
if (count > maxVotes) {
maxVotes = count;
ans = arr[i];
}
// If votes are equal, choose the lexicographically
// smaller name
else if (count === maxVotes && arr[i] < ans) {
ans = arr[i];
}
}
return [ ans, maxVotes.toString() ];
}
// Driver code
const arr = [
"john", "johnny", "jackie", "johnny", "john", "jackie",
"jamie", "jamie", "john", "johnny", "jamie", "johnny",
"john"
];
const ans = winner(arr);
console.log(ans[0] + " " + ans[1]);
Output
john 4
[Expected Approach] Using Hash Map - O(n) Time and O(n) Space
We traverse the array once and store vote count of every candidate in a hash map. Then, traverse the hash map to find the candidate with the highest vote count. If multiple candidates have the same maximum votes, choose the lexicographically smaller candidate.
- Create a hash map to store the vote count of each candidate.
- Traverse the array and increment the vote count of each candidate in the hash map.
- Initialize maxVotes as 0 and winner as an empty string.
- Traverse all entries of the hash map.
- If the current candidate has more votes than maxVotes, update maxVotes and winner.
- If the current candidate has the same number of votes, update winner only if its name is lexicographically smaller.
- Return the winner along with maxVotes.
#include <bits/stdc++.h>
using namespace std;
// Function to find the candidate with the maximum votes
vector<string> winner(vector<string> &arr)
{
unordered_map<string, int> mp;
// Store the vote count of every candidate
for (auto &name : arr)
mp[name]++;
string ans = "";
int maxVotes = 0;
// Find the candidate with the maximum votes
for (auto &entry : mp)
{
if (entry.second > maxVotes)
{
maxVotes = entry.second;
ans = entry.first;
}
// If votes are equal, choose the lexicographically smaller name
else if (entry.second == maxVotes && entry.first < ans)
{
ans = entry.first;
}
}
return {ans, to_string(maxVotes)};
}
// Driver code
int main()
{
vector<string> arr = {"john", "johnny", "jackie", "johnny", "john", "jackie", "jamie",
"jamie", "john", "johnny", "jamie", "johnny", "john"};
vector<string> ans = winner(arr);
cout << ans[0] << " " << ans[1] << endl;
return 0;
}
import java.util.*;
class GFG {
// Function to find the candidate with the maximum votes
static ArrayList<String> winner(String[] arr)
{
HashMap<String, Integer> map = new HashMap<>();
// Store the vote count of every candidate
for (String name : arr)
map.put(name, map.getOrDefault(name, 0) + 1);
String ans = "";
int maxVotes = 0;
// Find the candidate with the maximum votes
for (Map.Entry<String, Integer> entry :
map.entrySet()) {
if (entry.getValue() > maxVotes) {
maxVotes = entry.getValue();
ans = entry.getKey();
}
// If votes are equal, choose the
// lexicographically smaller name
else if (entry.getValue() == maxVotes
&& entry.getKey().compareTo(ans) < 0) {
ans = entry.getKey();
}
}
ArrayList<String> result = new ArrayList<>();
result.add(ans);
result.add(String.valueOf(maxVotes));
return result;
}
// Driver code
public static void main(String[] args)
{
String[] arr
= { "john", "johnny", "jackie", "johnny",
"john", "jackie", "jamie", "jamie",
"john", "johnny", "jamie", "johnny",
"john" };
ArrayList<String> ans = winner(arr);
System.out.println(ans.get(0) + " " + ans.get(1));
}
}
# Function to find the candidate with the maximum votes
def winner(arr):
mp = {}
# Store the vote count of every candidate
for name in arr:
mp[name] = mp.get(name, 0) + 1
ans = ""
maxVotes = 0
# Find the candidate with the maximum votes
for name, count in mp.items():
if count > maxVotes:
maxVotes = count
ans = name
# If votes are equal, choose the lexicographically smaller name
elif count == maxVotes and name < ans:
ans = name
return [ans, str(maxVotes)]
# Driver code
if __name__ == "__main__":
arr = [
"john", "johnny", "jackie", "johnny",
"john", "jackie", "jamie", "jamie",
"john", "johnny", "jamie", "johnny",
"john"
]
ans = winner(arr)
print(ans[0], ans[1])
using System;
using System.Collections.Generic;
class GFG {
// Function to find the candidate with the maximum votes
static List<string> winner(List<string> arr)
{
Dictionary<string, int> map
= new Dictionary<string, int>();
// Store the vote count of every candidate
foreach(string name in arr)
{
if (map.ContainsKey(name))
map[name]++;
else
map[name] = 1;
}
string ans = "";
int maxVotes = 0;
// Find the candidate with the maximum votes
foreach(KeyValuePair<string, int> entry in map)
{
if (entry.Value > maxVotes) {
maxVotes = entry.Value;
ans = entry.Key;
}
// If votes are equal, choose the
// lexicographically smaller name
else if (entry.Value == maxVotes
&& string.Compare(entry.Key, ans)
< 0) {
ans = entry.Key;
}
}
return new List<string>{ ans, maxVotes.ToString() };
}
// Driver code
static void Main()
{
List<string> arr = new List<string>{
"john", "johnny", "jackie", "johnny",
"john", "jackie", "jamie", "jamie",
"john", "johnny", "jamie", "johnny",
"john"
};
List<string> ans = winner(arr);
Console.WriteLine(ans[0] + " " + ans[1]);
}
}
// Function to find the candidate with the maximum votes
function winner(arr)
{
const map = new Map();
// Store the vote count of every candidate
for (const name of arr)
map.set(name, (map.get(name) || 0) + 1);
let ans = "";
let maxVotes = 0;
// Find the candidate with the maximum votes
for (const [name, count] of map) {
if (count > maxVotes) {
maxVotes = count;
ans = name;
}
// If votes are equal, choose the lexicographically
// smaller name
else if (count === maxVotes && name < ans) {
ans = name;
}
}
return [ ans, maxVotes.toString() ];
}
// Driver code
const arr = [
"john", "johnny", "jackie", "johnny", "john", "jackie",
"jamie", "jamie", "john", "johnny", "jamie", "johnny",
"john"
];
const ans = winner(arr);
console.log(ans[0] + " " + ans[1]);
Output
john 4
Another efficient solution is to use Trie. Please refer most frequent word in an array of strings.