Click here to Skip to main content
15,887,267 members
Please Sign up or sign in to vote.
0.00/5 (No votes)
See more:
A teacher is marking a bunch of English assignments and is running out of time. In order to expedite the marking process the teacher has decided that he will fail any assignment that has bad spelling, typos or incorrect capitalisation (or capitalization).

Write a function, in any language you choose, that will take a piece of text and decide if it passes muster. It's up to you to decide what constitutes a "bad" piece of text. You may even want to score it, but a simple yay / nay is OK, too.

Some examples of text you may be presented with:

"The quick brown fox jumped over the lazy dog"
"The quick brown fox jumped over the lazy dog."

"Its a rainy day today"

"i was walking along beach"

"Does this sentence have have a double word?"

"Am I missing a question mark."

"I looking for dog"

Some resources:


Points are awarded for elegance and completeness. The challenge here is to take a complex task and produce a solution that balances using the minimum effort with finding a complete solution. The task is to trim the teacher's workload, so every little bit helps. And maybe a couple of aspirins.
Posted
Updated 31-Mar-17 7:24am
Comments
Richard Deeming 31-Mar-17 10:00am    
The winner presumably gets to sell their solution to Microsoft, to replace the close-but-no-cigar grammar checker from Office? :)
PIEBALDconsult 31-Mar-17 10:01am    
"bad spelling, typos or incorrect capitalisation"
"poor spelling, typos, or incorrect capitalisation"
FTFY
ZurdoDev 31-Mar-17 10:39am    
Does Grammarly have an api? ;)

1 solution

Here is a quick 'n' dirty solution using an API service. Sadly the service is not as good as Grammarly...
C#
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;
using System.IO;
using System.Net;

namespace TextGearsApi
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine("Coding challenge: detect poor grammar");
            Console.WriteLine("=====================================\n");

            // Get you API key here: https://textgears.com
            var api = new TextGearsApi("[key_goes_here");

            for (;;)
            {
                Console.Write("Text to check: ");
                var text = Console.ReadLine();
                if (string.IsNullOrEmpty(text)) break;

                try
                {
                    var result = api.Check(text);
                    if (result?.Errors?.Count != 0)
                    {
                        Console.WriteLine("Recommendations:");
                        for (int i = 0; i < result.Errors.Count; i++)
                        {
                            var item = result.Errors[i];
                            Console.WriteLine($"  {i + 1}: {item.Bad} >> {string.Join(", ", item.Better.Select(x => $"\"{x}\""))}");
                        }
                        Console.WriteLine();
                    }
                    else
                    {
                        Console.WriteLine("Looks okay.\n");
                    }
                }
                catch (Exception ex)
                {
                    Console.WriteLine($"**Error: {ex.Message}\n");
                }
            }
        }
    }

    class TextGearsApi
    {
        
        public TextGearsApi(string key)
        {
            Key = key;
        }

        public string Key { get; private set; }

        public CheckResult Check(string text)
        {
            var request = WebRequest.Create($"https://api.textgears.com/check.php?text={WebUtility.UrlEncode(text)}&key={Key}") as HttpWebRequest;
            WebResponse response = null;
            try
            {
                response = request.GetResponse();

                if (response != null)
                {
                    var xxx = response.GetResponseStream();
                    using (var reader = new StreamReader(response.GetResponseStream()))
                    {
                        string data = reader.ReadToEnd();
                        return JsonConvert.DeserializeObject<CheckResult>(data);
                    }
                }
            }
            catch (Exception)
            {
                throw;
            }
            return null;
        }
    }

    public class CheckResult
    {
        [JsonProperty("result")]
        public bool Result { get; set; }

        [JsonProperty("errors")]
        public IList<Error> Errors { get; set; }

        [JsonProperty("score")]
        public int Score { get; set; }
    }

    public class Error
    {
        [JsonProperty("id")]
        public string Id { get; set; }

        [JsonProperty("offset")]
        public int Offset { get; set; }

        [JsonProperty("length")]
        public int Length { get; set; }

        [JsonProperty("bad")]
        public string Bad { get; set; }

        [JsonProperty("better")]
        public IList<string> Better { get; set; }
    }
}

Output:
Coding challenge: detect poor grammar
=====================================

Text to check: The quick brown fox jumped over the lazy dog
Looks okay.

Text to check: Its a rainy day today
Recommendations:
  1: Its a >> "It's a"
  2: Its >> "It's", "It is"

Text to check: i was walking along beach
Recommendations:
  1: i >> "I"

Text to check: Does this sentence have have a double word?
Recommendations:
  1: have have >> "have"
  2: have >> "had"

Text to check: Am I missing a question mark.
Looks okay.

Text to check: I looking for dog
Looks okay.

Will keep looking for a better service or solution...

UPDATE #1: Found a more accurate service called Ginger. Still not as good as Grammarly...
C#
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;
using System.IO;
using System.Net;

namespace GingerIt
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine("Coding challenge: detect poor grammar");
            Console.WriteLine("=====================================\n");

            var api = new GingerItApi();

            for (;;)
            {
                Console.Write("Text to check: ");
                var text = Console.ReadLine();
                if (string.IsNullOrEmpty(text)) break;

                try
                {
                    var result = api.Check(text);
                    if (result?.Corrections?.Count != 0)
                    {
                        Console.WriteLine("Recommendations:");
                        for (int i = 0; i < result.Corrections.Count; i++)
                        {
                            var item = result.Corrections[i];
                            var mistakes = string.Join(", ", item.Mistakes.Select(x => $"\"{text.Substring(x.From, x.To - x.From + 1)}\""));
                            var suggestions = string.Join(", ", item.Suggestions.Select(x => $"\"{x.Text}\""));
                            Console.WriteLine($"  {i + 1}: {mistakes} >> {suggestions}");
                        }
                        Console.WriteLine();
                    }
                    else
                    {
                        Console.WriteLine("Looks okay.\n");
                    }
                }
                catch (Exception ex)
                {
                    Console.WriteLine($"**Error: {ex.Message}\n");
                }
            }
        }
    }

    class GingerItApi
    {
        public CheckResult Check(string text)
        {
            var request = WebRequest.Create($"https://services.gingersoftware.com/Ginger/correct/jsonSecured/GingerTheTextFull?callback=jQuery172015406464511272344_1490987331365&apiKey=GingerWebSite&lang=US&clientVersion=2.0&text={text}&_=1490987518060") as HttpWebRequest;
            WebResponse response = null;
            try
            {
                response = request.GetResponse();

                if (response != null)
                {
                    using (var reader = new StreamReader(response.GetResponseStream()))
                    {
                        string data = reader.ReadToEnd();
                        var first = data.IndexOf('{');
                        var last = data.LastIndexOf('}');
                        var json = data.Substring(first, last - first + 1);
                        return JsonConvert.DeserializeObject<CheckResult>(json);
                    }
                }
            }
            catch (Exception)
            {
                throw;
            }
            return null;
        }
    }

    public class LrnFrgOrigIndx
    {
        [JsonProperty("From")]
        public int From { get; set; }

        [JsonProperty("To")]
        public int To { get; set; }
    }

    public class Mistake
    {
        [JsonProperty("Definition")]
        public string Definition { get; set; }

        [JsonProperty("CanAddToDict")]
        public bool CanAddToDict { get; set; }

        [JsonProperty("From")]
        public int From { get; set; }

        [JsonProperty("To")]
        public int To { get; set; }
    }

    public class Suggestion
    {
        [JsonProperty("Definition")]
        public string Definition { get; set; }

        [JsonProperty("LrnCatId")]
        public int LrnCatId { get; set; }

        [JsonProperty("Text")]
        public string Text { get; set; }
    }

    public class Correction
    {
        [JsonProperty("Confidence")]
        public int Confidence { get; set; }

        [JsonProperty("From")]
        public int From { get; set; }

        [JsonProperty("LrnFrg")]
        public string LrnFrg { get; set; }

        [JsonProperty("LrnFrgOrigIndxs")]
        public IList<LrnFrgOrigIndx> LrnFrgOrigIndxs { get; set; }

        [JsonProperty("Mistakes")]
        public IList<Mistake> Mistakes { get; set; }

        [JsonProperty("ShouldReplace")]
        public bool ShouldReplace { get; set; }

        [JsonProperty("Suggestions")]
        public IList<Suggestion> Suggestions { get; set; }

        [JsonProperty("To")]
        public int To { get; set; }

        [JsonProperty("TopLrnCatId")]
        public int TopLrnCatId { get; set; }

        [JsonProperty("Type")]
        public int Type { get; set; }

        [JsonProperty("UXFrgFrom")]
        public int UXFrgFrom { get; set; }

        [JsonProperty("UXFrgTo")]
        public int UXFrgTo { get; set; }
    }

    public class Sentence
    {
        [JsonProperty("FromIndex")]
        public int FromIndex { get; set; }

        [JsonProperty("IsEnglish")]
        public bool IsEnglish { get; set; }

        [JsonProperty("ToIndex")]
        public int ToIndex { get; set; }
    }

    public class CheckResult
    {
        [JsonProperty("Corrections")]
        public IList<Correction> Corrections { get; set; }

        [JsonProperty("Sentences")]
        public IList<Sentence> Sentences { get; set; }
    }
}

Output:
Coding challenge: detect poor grammar
=====================================

Text to check: The quick brown fox jumped over the lazy dog
Looks okay.

Text to check: Its a rainy day today
Recommendations:
  1: "Its" >> "It's"

Text to check: i was walking along beach
Recommendations:
  1: "i" >> "I"
  2: "beach" >> "the beach", "a beach"

Text to check: Does this sentence have have a double word?
Recommendations:
  1: "Does", "this", "sentence", "have", "have" >> "Is this sentence having", "Has this sentence had"

Text to check: Am I missing a question mark.
Looks okay.

Text to check: I looking for dog
Recommendations:
  1: "looking" >> "am looking", "look"
  2: "dog" >> "a dog"

More work to be done...
 
Share this answer
 
v5

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900