We had a programming quiz couple of weeks back at Devpinoy.org.. there where 5 people who dared to take on the quiz but sadly nobody got the correct answer after two rounds of testing(i guess i was pretty strict with my test cases) in the end i decided to just give the prize to the person who got the most correct program(15 out of 17 test cases). All in all it was a fun event...
anyway, i decided to post my answer to the quiz that i gave so that people could see how i solved the quiz(btw, this is not perfectly refactored so don't whine if you see some code smells in it...)
The Test Case
using System;using System.Collections.Generic;using System.Text;using NUnit;using NUnit.Framework;using System.Diagnostics;namespace KeithRull.BrainSharpeners{ [TestFixture] public class TestWordCount { private WordCount _wordCount; [SetUp] public void SetUp() { _wordCount = new WordCount(); } [Test] public void Test1() { string phraseToEvaluate = "this is a long text consist of different words."; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(9, count); } [Test] public void Test2() { string phraseToEvaluate = "\"this is a long text consist of different words.\""; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(1, count); } [Test] public void Test3() { string phraseToEvaluate = "this \"is a long\" text consist \"of different words."; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(7, count); } [Test] public void Test4() { string phraseToEvaluate = "\"this is a long text consist of different words."; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(9, count); } [Test] public void Test5() { string phraseToEvaluate = "this is a long text consist of different words.\""; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(9, count); } [Test] public void Test6() { string phraseToEvaluate = "\"\"this is a long text consist of different words."; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(9, count); } [Test] public void Test7() { string phraseToEvaluate = "this is a long text consist of different words.\"\""; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(9, count); } [Test] public void Test8() { string phraseToEvaluate = "this is a long text\"\" consist of different words."; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(9, count); } [Test] public void Test9() { string phraseToEvaluate = "this is a long text \"\" consist of different words."; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(9, count); } [Test] public void Test10() { string phraseToEvaluate = "this is a long text consist of different words."; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(9, count); } [Test] public void Test11() { string phraseToEvaluate = "this is a long text consist of different words."; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(9, count); } [Test] public void Test12() { string phraseToEvaluate = ""; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(0, count); } [Test] public void Test13() { string phraseToEvaluate = "\"this is a long\"\" text consist of different words.\""; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(2, count); } [Test] public void Test14() { string phraseToEvaluate = "this is a long\"text consist of different words."; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(8, count); } [Test] public void Test15() { string phraseToEvaluate = "\"this is a long\"\"text consist of different words.\""; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(2, count); } [Test] public void Test16() { string phraseToEvaluate = " this is a long\"\"text consist of different words."; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(8, count); } [Test] public void Test17() { string phraseToEvaluate = " this is a long\"\"text consist of different words. "; int count = _wordCount.CountNumberOfWordsFrom(phraseToEvaluate); Assert.AreEqual(8, count); } }}
My Solution
using System;using System.Collections.Generic;using System.Text;namespace KeithRull.BrainSharpeners{ /* Given a sentence or phrase, return all the words that exist in a phrase. Each word is delimited by a space. NOTE that words that are wrapped in quotes ("") are considered one word. Oh, and no, you can't use built in string library functions like Split. * */ class WordCount { const char CHAR_DoubleQuote = '"'; const char CHAR_WhiteSpace = ' '; public int CountNumberOfWordsFrom(string phrase) { int count = 0; string lastWord = string.Empty; bool jumped = false; string phraseToEvaluate = Trim(phrase); int phraseLenght = phraseToEvaluate.Length; if (phraseLenght != 0) { char[] phraseCharArray = ConvertToCharArrayFrom(phraseToEvaluate); for (int currentIndex = 0; currentIndex < phraseLenght; currentIndex++) { char lookUpChar = phraseCharArray[currentIndex]; if (IsWhiteSpace(lookUpChar)) { if (IsValidWord(lastWord)) { count++; } lastWord = string.Empty; jumped = false; } else if (IsDoubleQuote(lookUpChar)) { if (jumped) count++; jumped = false; int quotePairIndex = 0; int nextIndex = currentIndex + 1; quotePairIndex = FindCharIndex(phraseCharArray, CHAR_DoubleQuote, nextIndex); if ((nextIndex != quotePairIndex) && (quotePairIndex != -1)) { if (quotePairIndex <= phraseLenght) { lastWord = GetSubStringFromArray(phraseCharArray, currentIndex,quotePairIndex); jumped = true; currentIndex = quotePairIndex; } } } else if (jumped) { count++; lastWord += phraseCharArray[currentIndex]; jumped = false; } else { lastWord += phraseCharArray[currentIndex]; jumped = false; } } count++; } return count; } private bool IsValidWord(string word) { return word.Length > 0 && word != "\"\"" && word != " "; } public int FindCharIndex(char[] param, char itemToFind,int startIndex) { int position = -1; for (int index = startIndex; index < param.Length; index++) { if (param[index].Equals(itemToFind)) return index; } return position; } public string GetSubStringFromArray(char[] source, int startIndex, int endIndex) { string word = string.Empty; for (int index = startIndex; index < endIndex; index++) { word += source[index]; } return word; } public char[] ConvertToCharArrayFrom(string phrase) { char[] characterBucket = new char[phrase.Length]; int phraseLength = phrase.Length; for (int index = 0; index < phraseLength; index++) { characterBucket[index] = phrase[index]; } return characterBucket; } public bool CompareChar(char targetChar, char compareToChar) { return targetChar == compareToChar; } public bool IsWhiteSpace(char compareToChar) { return CompareChar(CHAR_WhiteSpace, compareToChar); } public bool IsDoubleQuote(char compareToChar) { return CompareChar(CHAR_DoubleQuote, compareToChar); } public string Trim(string phrase) { string trimmed = string.Empty; if (phrase.Length != 0) { trimmed = LTrim(RTrim(phrase)); } return trimmed; } public string LTrim(string phrase) { int indexOfValidChar = 0; char[] characterBucket = ConvertToCharArrayFrom(phrase); while (IsWhiteSpace(characterBucket[indexOfValidChar])) { indexOfValidChar++; } return GetSubStringFromArray(characterBucket, indexOfValidChar, phrase.Length); } public string RTrim(string phrase) { char[] characterBucket = ConvertToCharArrayFrom(phrase); int indexOfValidChar = characterBucket.Length - 1; while (IsWhiteSpace(characterBucket[indexOfValidChar])) { indexOfValidChar--; } return GetSubStringFromArray(characterBucket, 0, indexOfValidChar + 1); } }}
Good mind exercise if you ask me.
Disclaimer The opinions expressed herein are my own personal opinions and do not represent my employer's view in any way.