patterncsharpMinor
Pangrams implementation using Linq
Viewed 0 times
implementationlinqusingpangrams
Problem
This is a continuation of my LINQ stories from Pangrams-Hackerrank. Similarly, this challenge has been asked before in python Pangrams python Implementation but I have tried to accomplish this challenge using LINQ.
Here is a summary of the question
Roy wanted to increase his typing speed for programming contests. So, his friend advised him to type the sentence "The quick brown fox jumps over the lazy dog" repeatedly, because it is a pangram. (Pangrams are sentences constructed by using every letter of the alphabet at least once.)
After typing the sentence several times, Roy became bored with it. So he started to look for other pangrams.
Given a sentence , tell Roy if it is a pangram or not.
Input Format
Input consists of a string .
Constraints
Length of can be at most 103(1≤|s|≤103) and it may contain spaces, lower case and upper case letters. Lower-case and upper-case instances of a letter are considered the same.
Output Format
Output a line containing
Sample Input
Input #1
Input #2
Sample Output
Output #1
Output #2
Explanation
In the first test case, the answer is pangram because the sentence contains all the letters of the English alphabet.
Here is my implementation
```
using System;
using System.Collections.Generic;
using System.Collections;
using System.Linq;
using System.IO;
class Solution {
static void Main(String[] args) {
/ Enter your code here. Read input from STDIN. Print output to STDOUT. Your class should be named Solution /
string pangramInput = Console.ReadLine();
var alphabet = Enumerable.Range(97, 26).Select((x) => (char)x);
var pangramCheck = pangramInput.Replace(" ", "").ToLower().OrderBy((letter) => letter).Dis
Here is a summary of the question
Roy wanted to increase his typing speed for programming contests. So, his friend advised him to type the sentence "The quick brown fox jumps over the lazy dog" repeatedly, because it is a pangram. (Pangrams are sentences constructed by using every letter of the alphabet at least once.)
After typing the sentence several times, Roy became bored with it. So he started to look for other pangrams.
Given a sentence , tell Roy if it is a pangram or not.
Input Format
Input consists of a string .
Constraints
Length of can be at most 103(1≤|s|≤103) and it may contain spaces, lower case and upper case letters. Lower-case and upper-case instances of a letter are considered the same.
Output Format
Output a line containing
pangram if is a pangram, otherwise output not pangram.Sample Input
Input #1
We promptly judged antique ivory buckles for the next prize
Input #2
We promptly judged antique ivory buckles for the prize
Sample Output
Output #1
pangramOutput #2
not pangramExplanation
In the first test case, the answer is pangram because the sentence contains all the letters of the English alphabet.
Here is my implementation
```
using System;
using System.Collections.Generic;
using System.Collections;
using System.Linq;
using System.IO;
class Solution {
static void Main(String[] args) {
/ Enter your code here. Read input from STDIN. Print output to STDOUT. Your class should be named Solution /
string pangramInput = Console.ReadLine();
var alphabet = Enumerable.Range(97, 26).Select((x) => (char)x);
var pangramCheck = pangramInput.Replace(" ", "").ToLower().OrderBy((letter) => letter).Dis
Solution
First a review...
Long extension chains
With lengthy linq chains it's a good idea to break them into multiple lines. Especially here on CR so that we don't have to scroll horizontally.
String interpolation
We could optimize it as:
or you can make it even prettier by encapsulating this logic in an extension:
so you then have:
Consistency
Don't you like
Magic numbers
This would be easier to understand if you used constants:
Not LINQ
This two kill the linq idea of your question. Consider this instead:
Alternative solution
Then an alternative version...
If using a
UPDATE
Well, I forgot that we don't have to scan the entire string. As soon as we have the required chars we can stop. So this improved version should be faster for long texts:
Long extension chains
With lengthy linq chains it's a good idea to break them into multiple lines. Especially here on CR so that we don't have to scroll horizontally.
String interpolation
string answer = pangramCheck ? "pangram" : "not pangram";We could optimize it as:
var answer = $"{(pangramCheck ? string.Empty : "not ")}pangram";or you can make it even prettier by encapsulating this logic in an extension:
public static string Negate(this string value, bool negate)
{
return $"{(negate ? string.Empty : "not ")}{value}";
}so you then have:
Console.WriteLine("pangram".Negate(isPangram));Consistency
string text
string answerDon't you like
var for strings because you already use for the other two variables? ;-)Magic numbers
Enumerable.Range(97, 26)This would be easier to understand if you used constants:
const string alphabetLength = z - a + 1;
Enumerable.Range('a', alphabetLength)Not LINQ
.Replace(" ", "").ToLower()This two kill the linq idea of your question. Consider this instead:
text
.Select(char.ToLower)
.Where(char.IsLetter)Alternative solution
Then an alternative version...
If using a
HashSet is still linq-ish enougth then I replaced the Distinct with the Aggregate that uses one and makes it na O(n) solution for the English aphabet:const int alphabetLength = 'z' - 'a' + 1;
var isPangram =
text
.Select(char.ToLower)
.Where(char.IsLetter)
.Aggregate(new HashSet(), (acc, next) => { acc.Add(next); return acc; })
.Count == alphabetLength;UPDATE
Well, I forgot that we don't have to scan the entire string. As soon as we have the required chars we can stop. So this improved version should be faster for long texts:
const int alphabetLength = 'z' - 'a' + 1;
var chars = new HashSet();
var testedChars = text
.Select(char.ToLower)
.Where(char.IsLetter)
.TakeWhile(x => { chars.Add(x); return chars.Count != alphabetLength; })
.Count();
var isPangram = chars.Count == alphabetLength;Code Snippets
string answer = pangramCheck ? "pangram" : "not pangram";var answer = $"{(pangramCheck ? string.Empty : "not ")}pangram";public static string Negate(this string value, bool negate)
{
return $"{(negate ? string.Empty : "not ")}{value}";
}Console.WriteLine("pangram".Negate(isPangram));string text
string answerContext
StackExchange Code Review Q#145790, answer score: 4
Revisions (0)
No revisions yet.