├── LICENSE.txt ├── 9781430247616.jpg ├── 061_ConstructBinaryTree.cpp ├── README.md ├── Utility ├── list.h ├── BinaryTree.h ├── BinaryTree.cpp └── list.cpp ├── contributing.md ├── 104_SealedClass.cpp ├── 076_FirstNotRepeatingChar.cpp ├── 090_ContinousSequenceWithSum.java ├── 004_Scheduler.java ├── 065_StringPermutation.c ├── 035_NumberOf1.c ├── 037_ModifyANumberToAnother.c ├── 066_EightQueens.c ├── 095_DicesProbability.cpp ├── 048_ReverseList.cpp ├── 034_MinimalPresses.cs ├── 072_GreatestSumOfSubarrays.java ├── 079_DelelteDuplicatedCharacters.c ├── 013_PrintListsReversely.cpp ├── 028_TurningNumber.java ├── 087_TwoNumbersWithSum.java ├── 077_FirstCharAppearingOnce.cpp ├── 001_PalindromeNumber.c ├── 074_SortArrayForMinNumber.java ├── 021_QueueWithTwoStacks.cs ├── 040_Power.cpp ├── 005_Duplication.java ├── 080_Anagram.java ├── 068_StringCombination.java ├── 022_StackWithTwoQueues.cs ├── 096_LastNumberInCircle.cpp ├── 106_StringToInt.cpp ├── 012_NumericStrings.cpp ├── 091_ReverseWordsInSentence.cpp ├── 027_ArrayRotation.java ├── 105_ConstuctArray.java ├── 092_LeftRotateString.cpp ├── 031_RobotMove.cpp ├── 041_Print1ToMaxOfNDigits.cpp ├── 002_AssignmentOperator.cpp ├── 011_SimpleRegularExpression.cpp ├── 033_CoinChanges.cs ├── 088_ThreeNumbersWithSum.java ├── 094_QueueWithMax.cpp ├── 007_FindInSortedMatrix.java ├── 067_ArrayPermutation.java ├── 078_DelelteCharacters.c ├── 056_StackPushPopOrder.cpp ├── 089_SubsetWithSum.java ├── 069_MedianStream.cpp ├── 063_SequenceOfBST.cpp ├── 006_Duplication.java ├── 073_NumberOf1.c ├── 032_EditDistance.cs ├── 010_MergeSortedArrays.c ├── 038_NumbersOccuringOnce.java ├── 098_MaximalProfitBuyingSellingStock.cpp ├── 003_Singleton.cs ├── 075_UglyNumbers.cs ├── 085_TreeDepth.cpp ├── 023_Fibonacci.c ├── 043_DeleteNodeInList.cpp ├── 100_103_ArithmeticOperations.java ├── 009_ReplaceBlanks.c ├── 057_PrintTreeByLevel.cpp ├── 099_Accumulate.cpp ├── 097_MinimalMoves.java ├── 042_AddNumericStrings.c ├── 045_ReorderNumbers.java ├── 081_ReversedPairs.java ├── 046_RemoveNumbers.java ├── 047_KthNodeFromEnd.cpp ├── 053_PrintMatrix.java ├── 016_LoopsInLists.cpp ├── 049_ReverseListInGroups.cpp └── 071_ArrayIntersection.cpp /LICENSE.txt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Apress/coding-interviews/HEAD/LICENSE.txt -------------------------------------------------------------------------------- /9781430247616.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Apress/coding-interviews/HEAD/9781430247616.jpg -------------------------------------------------------------------------------- /061_ConstructBinaryTree.cpp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/Apress/coding-interviews/HEAD/061_ConstructBinaryTree.cpp -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Apress Source Code 2 | 3 | This repository accompanies [*Coding Interviews*](http://www.apress.com/9781430247616) by Harry He (Apress, 2012). 4 | 5 | ![Cover image](9781430247616.jpg) 6 | 7 | Download the files as a zip using the green button, or clone the repository to your machine using Git. 8 | 9 | ## Releases 10 | 11 | Release v1.0 corresponds to the code in the published book, without corrections or updates. 12 | 13 | ## Contributions 14 | 15 | See the file Contributing.md for more information on how you can contribute to this repository. 16 | -------------------------------------------------------------------------------- /Utility/list.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | struct ListNode 4 | { 5 | int m_nValue; 6 | ListNode* m_pNext; 7 | }; 8 | 9 | __declspec( dllexport ) ListNode* CreateListNode(int value); 10 | __declspec( dllexport ) void ConnectListNodes(ListNode* pCurrent, ListNode* pNext); 11 | __declspec( dllexport ) void PrintListNode(ListNode* pNode); 12 | __declspec( dllexport ) void PrintList(ListNode* pHead); 13 | __declspec( dllexport ) void DestroyList(ListNode* pHead); 14 | __declspec( dllexport ) void AddToTail(ListNode** pHead, int value); 15 | __declspec( dllexport ) void RemoveNode(ListNode** pHead, int value); -------------------------------------------------------------------------------- /Utility/BinaryTree.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | struct BinaryTreeNode 4 | { 5 | int m_nValue; 6 | BinaryTreeNode* m_pLeft; 7 | BinaryTreeNode* m_pRight; 8 | }; 9 | 10 | __declspec( dllexport ) BinaryTreeNode* CreateBinaryTreeNode(int value); 11 | __declspec( dllexport ) void ConnectTreeNodes(BinaryTreeNode* pParent, BinaryTreeNode* pLeft, BinaryTreeNode* pRight); 12 | __declspec( dllexport ) void PrintTreeNode(BinaryTreeNode* pNode); 13 | __declspec( dllexport ) void PrintTree(BinaryTreeNode* pRoot); 14 | __declspec( dllexport ) void DestroyTree(BinaryTreeNode* pRoot); 15 | -------------------------------------------------------------------------------- /contributing.md: -------------------------------------------------------------------------------- 1 | # Contributing to Apress Source Code 2 | 3 | Copyright for Apress source code belongs to the author(s). However, under fair use you are encouraged to fork and contribute minor corrections and updates for the benefit of the author(s) and other readers. 4 | 5 | ## How to Contribute 6 | 7 | 1. Make sure you have a GitHub account. 8 | 2. Fork the repository for the relevant book. 9 | 3. Create a new branch on which to make your change, e.g. 10 | `git checkout -b my_code_contribution` 11 | 4. Commit your change. Include a commit message describing the correction. Please note that if your commit message is not clear, the correction will not be accepted. 12 | 5. Submit a pull request. 13 | 14 | Thank you for your contribution! -------------------------------------------------------------------------------- /104_SealedClass.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | 6 | // ==================== Solution 1 ==================== 7 | class SealedClass1 8 | { 9 | public: 10 | static SealedClass1* GetInstance() 11 | { 12 | return new SealedClass1(); 13 | } 14 | 15 | static void DeleteInstance( SealedClass1* pInstance) 16 | { 17 | delete pInstance; 18 | } 19 | 20 | private: 21 | SealedClass1() {} 22 | ~SealedClass1() {} 23 | }; 24 | 25 | // It will cause compiling errors when we try to 26 | // define new classes deriving from SealedClass 27 | /* 28 | class Try1 : public SealedClass1 29 | { 30 | public: 31 | Try1() {} 32 | ~Try1() {} 33 | }; 34 | */ 35 | 36 | // ==================== Solution 2 ==================== 37 | // NOTE: It only works in Visual Studio, but does not 38 | // work in G++ 39 | template class MakeSealed 40 | { 41 | friend T; 42 | 43 | private: 44 | MakeSealed() {} 45 | ~MakeSealed() {} 46 | }; 47 | 48 | class SealedClass2 : virtual public MakeSealed 49 | { 50 | public: 51 | SealedClass2() {} 52 | ~SealedClass2() {} 53 | }; 54 | 55 | // It will cause compiling errors when we try to 56 | // define new classes deriving from SealedClass 57 | /* 58 | class Try2 : public SealedClass2 59 | { 60 | public: 61 | Try2() {} 62 | ~Try2() {} 63 | }; 64 | */ 65 | 66 | int main(int argc, char* argv[]) 67 | { 68 | return 0; 69 | } 70 | 71 | -------------------------------------------------------------------------------- /076_FirstNotRepeatingChar.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | char FirstNotRepeatingChar(char* pString) 8 | { 9 | if(pString == NULL) 10 | return '\0'; 11 | 12 | const int tableSize = 256; 13 | unsigned int hashTable[tableSize]; 14 | for(unsigned int i = 0; i sum && small < middle) { 19 | curSum -= small; 20 | ++small; 21 | 22 | if(curSum == sum) 23 | printContinuousSequence(small, big); 24 | } 25 | 26 | ++big; 27 | curSum += big; 28 | } 29 | } 30 | 31 | private static void printContinuousSequence(int small, int big){ 32 | for(int i = small; i <= big; ++i) 33 | System.out.print(String.valueOf(i) + " "); 34 | System.out.println(""); 35 | } 36 | 37 | // ==================== test code ==================== 38 | private static void test(String testName, int sum) { 39 | System.out.println(testName + " for " + String.valueOf(sum) + " begins: "); 40 | 41 | findContinuousSequence(sum); 42 | } 43 | 44 | public static void main(String[] args) { 45 | test("test1", 1); 46 | test("test2", 3); 47 | test("test3", 4); 48 | test("test4", 9); 49 | test("test5", 15); 50 | test("test6", 100); 51 | } 52 | } 53 | -------------------------------------------------------------------------------- /004_Scheduler.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | 5 | public class Scheduler { 6 | public class SimpleThread extends Thread{ 7 | private int value; 8 | public SimpleThread(int num) { 9 | this.value = num; 10 | 11 | start(); 12 | } 13 | 14 | public void run(){ 15 | while(true) { 16 | synchronized(this){ 17 | try { 18 | wait(); 19 | } catch (InterruptedException e) { 20 | throw new RuntimeException(e); 21 | } 22 | 23 | System.out.print(value + " "); 24 | } 25 | } 26 | } 27 | } 28 | 29 | static final int COUNT = 3; 30 | static final int SLEEP = 37; 31 | 32 | public static void main(String args[]) { 33 | Scheduler scheduler = new Scheduler(); 34 | SimpleThread threads[] = new SimpleThread[COUNT]; 35 | for(int i = 0; i < COUNT; ++i) 36 | threads[i] = scheduler.new SimpleThread(i + 1); 37 | 38 | int index = 0; 39 | while(true){ 40 | synchronized(threads[index]) { 41 | threads[index].notify(); 42 | } 43 | 44 | try { 45 | Thread.sleep(SLEEP); 46 | } catch (InterruptedException e) { 47 | throw new RuntimeException(e); 48 | } 49 | 50 | index = (++index) % COUNT; 51 | } 52 | } 53 | } 54 | 55 | -------------------------------------------------------------------------------- /065_StringPermutation.c: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | void PermutationCore(char* pStr, char* pBegin); 8 | 9 | void Permutation(char* pStr) 10 | { 11 | if(pStr == NULL) 12 | return; 13 | 14 | PermutationCore(pStr, pStr); 15 | } 16 | 17 | void PermutationCore(char* pStr, char* pBegin) 18 | { 19 | char *pCh = NULL; 20 | char temp; 21 | 22 | if(*pBegin == '\0') 23 | { 24 | printf("%s\n", pStr); 25 | } 26 | else 27 | { 28 | for(pCh = pBegin; *pCh != '\0'; ++ pCh) 29 | { 30 | temp = *pCh; 31 | *pCh = *pBegin; 32 | *pBegin = temp; 33 | 34 | PermutationCore(pStr, pBegin + 1); 35 | 36 | temp = *pCh; 37 | *pCh = *pBegin; 38 | *pBegin = temp; 39 | } 40 | } 41 | } 42 | 43 | // ==================== Test Code ==================== 44 | void Test(char* pStr) 45 | { 46 | if(pStr == NULL) 47 | printf("Test for NULL begins:\n"); 48 | else 49 | printf("Test for %s begins:\n", pStr); 50 | 51 | Permutation(pStr); 52 | 53 | printf("\n"); 54 | } 55 | 56 | int main(int argc, char* argv[]) 57 | { 58 | char string1[64]; 59 | char string2[64]; 60 | char string3[64]; 61 | char string4[64]; 62 | 63 | Test(NULL); 64 | 65 | string1[0] = '\0'; 66 | Test(string1); 67 | 68 | sprintf(string2, "%s", "a"); 69 | Test(string2); 70 | 71 | sprintf(string3, "%s", "ab"); 72 | Test(string3); 73 | 74 | sprintf(string4, "%s", "abc"); 75 | Test(string4); 76 | 77 | return 0; 78 | } 79 | 80 | -------------------------------------------------------------------------------- /035_NumberOf1.c: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | 6 | int NumberOf1_Solution1(int n) 7 | { 8 | int count = 0; 9 | unsigned int flag = 1; 10 | while(flag) 11 | { 12 | if(n & flag) 13 | count ++; 14 | 15 | flag = flag << 1; 16 | } 17 | 18 | return count; 19 | } 20 | 21 | int NumberOf1_Solution2(int n) 22 | { 23 | int count = 0; 24 | 25 | while (n) 26 | { 27 | ++ count; 28 | n = (n - 1) & n; 29 | } 30 | 31 | return count; 32 | } 33 | 34 | // ==================== Test Code ==================== 35 | void Test(int number, unsigned int expected) 36 | { 37 | int actual = NumberOf1_Solution1(number); 38 | if(actual == expected) 39 | printf("Solution1: Test for %p passed.\n", number); 40 | else 41 | printf("Solution1: Test for %p failed.\n", number); 42 | 43 | actual = NumberOf1_Solution2(number); 44 | if(actual == expected) 45 | printf("Solution2: Test for %p passed.\n", number); 46 | else 47 | printf("Solution2: Test for %p failed.\n", number); 48 | 49 | printf("\n"); 50 | } 51 | 52 | int main(int argc, char* argv[]) 53 | { 54 | // input 0, expected output is 0 55 | Test(0, 0); 56 | 57 | // input 1, expected output is 1 58 | Test(1, 1); 59 | 60 | // input 10, expected output is 2 61 | Test(10, 2); 62 | 63 | // input 0x7FFFFFFF, expected output is 31 64 | Test(0x7FFFFFFF, 31); 65 | 66 | // input 0xFFFFFFFF (negative), expected output is 32 67 | Test(0xFFFFFFFF, 32); 68 | 69 | // input 0x80000000 (negative), expected output is 1 70 | Test(0x80000000, 1); 71 | 72 | return 0; 73 | } 74 | -------------------------------------------------------------------------------- /037_ModifyANumberToAnother.c: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | 6 | int bitsToModify(int number1, int number2) 7 | { 8 | int temp = number1 ^ number2; 9 | 10 | // the number of 1 bits in temp 11 | int bits = 0; 12 | while(temp != 0) { 13 | ++bits; 14 | temp = (temp - 1) & temp; 15 | } 16 | 17 | return bits; 18 | } 19 | 20 | // ======== Test Code ======== 21 | void test(char* testName, int number1, int number2, int expected) 22 | { 23 | if(testName != NULL) 24 | printf("%s begins: ", testName); 25 | 26 | if(bitsToModify(number1, number2) == expected) 27 | printf("Passed.\n"); 28 | else 29 | printf("FAILED.\n"); 30 | } 31 | 32 | void test1() 33 | { 34 | int number1 = 0; 35 | int number2 = 13; 36 | int expected = 3; 37 | 38 | test("Test1", number1, number2, expected); 39 | } 40 | 41 | void test2() 42 | { 43 | int number1 = 0; 44 | int number2 = 15; 45 | int expected = 4; 46 | 47 | test("Test2", number1, number2, expected); 48 | } 49 | 50 | void test3() 51 | { 52 | int number1 = 7; 53 | int number2 = 0; 54 | int expected = 3; 55 | 56 | test("Test3", number1, number2, expected); 57 | } 58 | 59 | void test4() 60 | { 61 | int number1 = 7; 62 | int number2 = 7; 63 | int expected = 0; 64 | 65 | test("Test4", number1, number2, expected); 66 | } 67 | 68 | 69 | void test5() 70 | { 71 | int number1 = 7; 72 | int number2 = 15; 73 | int expected = 1; 74 | 75 | test("Test5", number1, number2, expected); 76 | } 77 | 78 | int main(int argc, char* argv[]) 79 | { 80 | test1(); 81 | test2(); 82 | test3(); 83 | test4(); 84 | test5(); 85 | } -------------------------------------------------------------------------------- /066_EightQueens.c: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | 6 | void Permutation(int columnIndex[], int length, int index, int* count); 7 | int Check(int ColumnIndex[], int length); 8 | 9 | int EightQueen() 10 | { 11 | int columnIndex[8] = {0, 1, 2, 3, 4, 5, 6, 7}; 12 | 13 | int count = 0; 14 | Permutation(columnIndex, 8, 0, &count); 15 | 16 | return count; 17 | } 18 | 19 | void Permutation(int columnIndex[], int length, int index, int* count) 20 | { 21 | int i, temp; 22 | 23 | if(index == length) 24 | { 25 | if(Check(columnIndex, length) != 0) 26 | { 27 | (*count)++; 28 | } 29 | } 30 | else 31 | { 32 | for(i = index; i < length; ++ i) 33 | { 34 | temp = columnIndex[i]; 35 | columnIndex[i] = columnIndex[index]; 36 | columnIndex[index] = temp; 37 | 38 | Permutation(columnIndex, length, index + 1, count); 39 | 40 | temp = columnIndex[index]; 41 | columnIndex[index] = columnIndex[i]; 42 | columnIndex[i] = temp; 43 | } 44 | } 45 | } 46 | 47 | /* If there are two queens on the same diagonal, it returns 0, 48 | otherwise it returns 1. */ 49 | int Check(int columnIndex[], int length) 50 | { 51 | int i, j; 52 | 53 | for(i = 0; i < length; ++ i) 54 | { 55 | for(j = i + 1; j < length; ++ j) 56 | { 57 | if((i - j == columnIndex[i] - columnIndex[j]) 58 | || (j - i == columnIndex[i] - columnIndex[j])) 59 | return 0; 60 | } 61 | } 62 | 63 | return 1; 64 | } 65 | 66 | int main(int argc, char* argv[]) 67 | { 68 | int count = EightQueen(); 69 | printf("The count of ways to place eight queens: %d.\n", count); 70 | } -------------------------------------------------------------------------------- /Utility/BinaryTree.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include "BinaryTree.h" 3 | 4 | BinaryTreeNode* CreateBinaryTreeNode(int value) 5 | { 6 | BinaryTreeNode* pNode = new BinaryTreeNode(); 7 | pNode->m_nValue = value; 8 | pNode->m_pLeft = NULL; 9 | pNode->m_pRight = NULL; 10 | 11 | return pNode; 12 | } 13 | 14 | void ConnectTreeNodes(BinaryTreeNode* pParent, BinaryTreeNode* pLeft, BinaryTreeNode* pRight) 15 | { 16 | if(pParent != NULL) 17 | { 18 | pParent->m_pLeft = pLeft; 19 | pParent->m_pRight = pRight; 20 | } 21 | } 22 | 23 | void PrintTreeNode(BinaryTreeNode* pNode) 24 | { 25 | if(pNode != NULL) 26 | { 27 | printf("value of this node is: %d\n", pNode->m_nValue); 28 | 29 | if(pNode->m_pLeft != NULL) 30 | printf("value of its left child is: %d.\n", pNode->m_pLeft->m_nValue); 31 | else 32 | printf("left child is null.\n"); 33 | 34 | if(pNode->m_pRight != NULL) 35 | printf("value of its right child is: %d.\n", pNode->m_pRight->m_nValue); 36 | else 37 | printf("right child is null.\n"); 38 | } 39 | else 40 | { 41 | printf("this node is null.\n"); 42 | } 43 | 44 | printf("\n"); 45 | } 46 | 47 | void PrintTree(BinaryTreeNode* pRoot) 48 | { 49 | PrintTreeNode(pRoot); 50 | 51 | if(pRoot != NULL) 52 | { 53 | if(pRoot->m_pLeft != NULL) 54 | PrintTree(pRoot->m_pLeft); 55 | 56 | if(pRoot->m_pRight != NULL) 57 | PrintTree(pRoot->m_pRight); 58 | } 59 | } 60 | 61 | void DestroyTree(BinaryTreeNode* pRoot) 62 | { 63 | if(pRoot != NULL) 64 | { 65 | BinaryTreeNode* pLeft = pRoot->m_pLeft; 66 | BinaryTreeNode* pRight = pRoot->m_pRight; 67 | 68 | delete pRoot; 69 | pRoot = NULL; 70 | 71 | DestroyTree(pLeft); 72 | DestroyTree(pRight); 73 | } 74 | } 75 | -------------------------------------------------------------------------------- /095_DicesProbability.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | void PrintProbability(int number) 8 | { 9 | if(number < 1) 10 | return; 11 | 12 | const int maxValue = 6; 13 | int* pProbabilities[2]; 14 | pProbabilities[0] = new int[maxValue * number + 1]; 15 | pProbabilities[1] = new int[maxValue * number + 1]; 16 | for(int i = 0; i < maxValue * number + 1; ++i) 17 | { 18 | pProbabilities[0][i] = 0; 19 | pProbabilities[1][i] = 0; 20 | } 21 | 22 | int flag = 0; 23 | for (int i = 1; i <= maxValue; ++i) 24 | pProbabilities[flag][i] = 1; 25 | 26 | for (int k = 2; k <= number; ++k) 27 | { 28 | for(int i = 0; i < k; ++i) 29 | pProbabilities[1 - flag][i] = 0; 30 | 31 | for (int i = k; i <= maxValue * k; ++i) 32 | { 33 | pProbabilities[1 - flag][i] = 0; 34 | for(int j = 1; j <= i && j <= maxValue; ++j) 35 | pProbabilities[1 - flag][i] += pProbabilities[flag][i - j]; 36 | } 37 | 38 | flag = 1 - flag; 39 | } 40 | 41 | double total = pow((double)maxValue, number); 42 | for(int i = number; i <= maxValue * number; ++i) 43 | { 44 | double ratio = (double)pProbabilities[flag][i] / total; 45 | printf("%d: %e\n", i, ratio); 46 | } 47 | 48 | delete[] pProbabilities[0]; 49 | delete[] pProbabilities[1]; 50 | } 51 | 52 | // ==================== Test Code ==================== 53 | void Test(int n) 54 | { 55 | printf("Test for %d begins:\n", n); 56 | 57 | PrintProbability(n); 58 | 59 | printf("\n"); 60 | } 61 | 62 | int main(int argc, char* argv[]) 63 | { 64 | Test(1); 65 | Test(2); 66 | Test(3); 67 | Test(4); 68 | 69 | Test(11); 70 | 71 | Test(0); 72 | 73 | return 0; 74 | } 75 | -------------------------------------------------------------------------------- /048_ReverseList.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include "..\Utility\List.h" 6 | 7 | ListNode* ReverseList(ListNode* pHead) 8 | { 9 | ListNode* pReversedHead = NULL; 10 | ListNode* pNode = pHead; 11 | ListNode* pPrev = NULL; 12 | while(pNode != NULL) 13 | { 14 | ListNode* pNext = pNode->m_pNext; 15 | 16 | if(pNext == NULL) 17 | pReversedHead = pNode; 18 | 19 | pNode->m_pNext = pPrev; 20 | 21 | pPrev = pNode; 22 | pNode = pNext; 23 | } 24 | 25 | return pReversedHead; 26 | } 27 | 28 | // ==================== Test Code ==================== 29 | ListNode* Test(ListNode* pHead) 30 | { 31 | printf("The original list is: \n"); 32 | PrintList(pHead); 33 | 34 | ListNode* pReversedHead = ReverseList(pHead); 35 | 36 | printf("The reversed list is: \n"); 37 | PrintList(pReversedHead); 38 | 39 | printf("\n"); 40 | 41 | return pReversedHead; 42 | } 43 | 44 | // Multiple nodes 45 | void Test1() 46 | { 47 | ListNode* pNode1 = CreateListNode(1); 48 | ListNode* pNode2 = CreateListNode(2); 49 | ListNode* pNode3 = CreateListNode(3); 50 | ListNode* pNode4 = CreateListNode(4); 51 | ListNode* pNode5 = CreateListNode(5); 52 | 53 | ConnectListNodes(pNode1, pNode2); 54 | ConnectListNodes(pNode2, pNode3); 55 | ConnectListNodes(pNode3, pNode4); 56 | ConnectListNodes(pNode4, pNode5); 57 | 58 | ListNode* pReversedHead = Test(pNode1); 59 | 60 | DestroyList(pReversedHead); 61 | } 62 | 63 | // Only one node 64 | void Test2() 65 | { 66 | ListNode* pNode1 = CreateListNode(1); 67 | 68 | ListNode* pReversedHead = Test(pNode1); 69 | 70 | DestroyList(pReversedHead); 71 | } 72 | 73 | // Empty list 74 | void Test3() 75 | { 76 | Test(NULL); 77 | } 78 | 79 | int main(int argc, char* argv[]) 80 | { 81 | Test1(); 82 | Test2(); 83 | Test3(); 84 | 85 | return 0; 86 | } 87 | -------------------------------------------------------------------------------- /034_MinimalPresses.cs: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | using System; 5 | using System.Collections.Generic; 6 | 7 | namespace _034_MinimalPresses 8 | { 9 | class Program 10 | { 11 | public static int MinKeyPress(int keys, int[] frequencies) 12 | { 13 | Array.Sort(frequencies); 14 | 15 | int letters = frequencies.Length; 16 | int presses = 0; 17 | 18 | // The last element has the highest frequency in 19 | // an increasingly sorted array 20 | for (int i = letters - 1; i >= 0; --i) 21 | { 22 | int j = letters - 1 - i; 23 | presses += frequencies[i] * (j / keys + 1); 24 | } 25 | 26 | return presses; 27 | } 28 | 29 | // ============================ test code ============================ 30 | private static void Test(String testName, int keys, int[] frequencies, int expected) 31 | { 32 | Console.Write(testName + " begins: "); 33 | 34 | if (MinKeyPress(keys, frequencies) == expected) 35 | Console.Write("Passed.\n"); 36 | else 37 | Console.Write("FAILED.\n"); 38 | } 39 | 40 | private static void Test1() 41 | { 42 | int keys = 9; 43 | int[] frequences = { 1, 1, 1, 100, 100, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 10, 11, 11, 11, 11, 1, 1, 1, 100 }; 44 | int expected = 397; 45 | 46 | Test("Test1", keys, frequences, expected); 47 | } 48 | 49 | private static void Test2() 50 | { 51 | int keys = 2; 52 | int[] frequences = { 8, 2, 5, 2, 4, 9 }; 53 | int expected = 47; 54 | 55 | Test("Test2", keys, frequences, expected); 56 | } 57 | 58 | static void Main(string[] args) 59 | { 60 | Test1(); 61 | Test2(); 62 | } 63 | } 64 | } 65 | -------------------------------------------------------------------------------- /072_GreatestSumOfSubarrays.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | public class GreatestSumOfSubarrays { 5 | public static int getGreatestSumOfSubArray(int[] numbers) { 6 | int curSum = 0; 7 | int greatestSum = Integer.MIN_VALUE; 8 | for(int i = 0; i < numbers.length; ++i) { 9 | if(curSum <= 0) 10 | curSum = numbers[i]; 11 | else 12 | curSum += numbers[i]; 13 | 14 | if(curSum > greatestSum) 15 | greatestSum = curSum; 16 | } 17 | 18 | return greatestSum; 19 | } 20 | 21 | //================= Test Code ================= 22 | 23 | private static void test(String testName, int[] numbers, int expected) { 24 | System.out.print(testName + " begins: "); 25 | 26 | if(getGreatestSumOfSubArray(numbers) == expected) 27 | System.out.print("passed.\n"); 28 | else 29 | System.out.print("FAILED.\n"); 30 | } 31 | 32 | private static void test1() { 33 | int[] numbers = {1, -2, 3, 10, -4, 7, 2, -5}; 34 | int expected = 18; 35 | test("Test1", numbers, expected); 36 | } 37 | 38 | // all numbers are negative 39 | private static void test2() { 40 | int[] numbers = {-2, -8, -1, -5, -9}; 41 | int expected = -1; 42 | test("Test2", numbers, expected); 43 | } 44 | 45 | // all numbers are positive 46 | private static void test3() { 47 | int[] numbers = {2, 8, 1, 5, 9}; 48 | int expected = 25; 49 | test("Test3", numbers, expected); 50 | } 51 | 52 | // only one number 53 | private static void test4() { 54 | int[] numbers = {2}; 55 | int expected = 2; 56 | test("Test4", numbers, expected); 57 | } 58 | 59 | public static void main(String[] argv) { 60 | test1(); 61 | test2(); 62 | test3(); 63 | test4(); 64 | } 65 | } 66 | -------------------------------------------------------------------------------- /079_DelelteDuplicatedCharacters.c: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | void DeletedDuplication(char* pString) 8 | { 9 | int hashTable[256]; 10 | char* pSlow = pString; 11 | char* pFast = pString; 12 | 13 | if(pString == NULL) 14 | return; 15 | 16 | memset(hashTable, 0, sizeof(hashTable)); 17 | 18 | while (*pFast != '\0') 19 | { 20 | *pSlow = *pFast; 21 | 22 | if(hashTable[*pFast] == 0) 23 | { 24 | ++ pSlow; 25 | hashTable[*pFast] = 1; 26 | } 27 | 28 | ++pFast; 29 | } 30 | 31 | *pSlow = '\0'; 32 | } 33 | 34 | // ==================== Test Code ==================== 35 | void Test(char* testName, char* pString, char* pExpected) 36 | { 37 | if(NULL != testName) 38 | printf("%s begins: ", testName); 39 | 40 | DeletedDuplication(pString); 41 | if((pString == NULL && pExpected == NULL) || (0 == strcmp(pString, pExpected))) 42 | printf("Passed.\n"); 43 | else 44 | printf("FAILED.\n"); 45 | } 46 | 47 | void Test1() 48 | { 49 | char pString[] = "google"; 50 | char* pExpected = "gole"; 51 | Test("Test1", pString, pExpected); 52 | } 53 | 54 | void Test2() 55 | { 56 | char pString[] = "aaaaaaaaaaaaaaaaaaaaa"; 57 | char* pExpected = "a"; 58 | Test("Test2", pString, pExpected); 59 | } 60 | 61 | void Test3() 62 | { 63 | char pString[] = ""; 64 | char* pExpected = ""; 65 | Test("Test3", pString, pExpected); 66 | } 67 | 68 | void Test4() 69 | { 70 | char pString[] = "abcacbbacbcacabcba"; 71 | char* pExpected = "abc"; 72 | Test("Test4", pString, pExpected); 73 | } 74 | 75 | void Test5() 76 | { 77 | char pString[] = "abcdefg"; 78 | char* pExpected = "abcdefg"; 79 | Test("Test5", pString, pExpected); 80 | } 81 | 82 | void Test6() 83 | { 84 | char* pString = NULL; 85 | char* pExpected = NULL; 86 | Test("Test6", pString, pExpected); 87 | } 88 | 89 | int main(int argc, char* argv[]) 90 | { 91 | Test1(); 92 | Test2(); 93 | Test3(); 94 | Test4(); 95 | Test5(); 96 | Test6(); 97 | } -------------------------------------------------------------------------------- /013_PrintListsReversely.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include "..\Utility\List.h" 6 | #include 7 | 8 | void PrintListReversingly_Iteratively(ListNode* pHead) 9 | { 10 | std::stack nodes; 11 | 12 | ListNode* pNode = pHead; 13 | while(pNode != NULL) 14 | { 15 | nodes.push(pNode); 16 | pNode = pNode->m_pNext; 17 | } 18 | 19 | while(!nodes.empty()) 20 | { 21 | pNode = nodes.top(); 22 | printf("%d\t", pNode->m_nValue); 23 | nodes.pop(); 24 | } 25 | } 26 | 27 | void PrintListReversingly_Recursively(ListNode* pHead) 28 | { 29 | if(pHead != NULL) 30 | { 31 | if (pHead->m_pNext != NULL) 32 | { 33 | PrintListReversingly_Recursively(pHead->m_pNext); 34 | } 35 | 36 | printf("%d\t", pHead->m_nValue); 37 | } 38 | } 39 | 40 | // ==================== Test Code ==================== 41 | 42 | void Test(ListNode* pHead) 43 | { 44 | PrintList(pHead); 45 | PrintListReversingly_Iteratively(pHead); 46 | printf("\n"); 47 | PrintListReversingly_Recursively(pHead); 48 | } 49 | 50 | // 1->2->3->4->5 51 | void Test1() 52 | { 53 | printf("\nTest1 begins.\n"); 54 | 55 | ListNode* pNode1 = CreateListNode(1); 56 | ListNode* pNode2 = CreateListNode(2); 57 | ListNode* pNode3 = CreateListNode(3); 58 | ListNode* pNode4 = CreateListNode(4); 59 | ListNode* pNode5 = CreateListNode(5); 60 | 61 | ConnectListNodes(pNode1, pNode2); 62 | ConnectListNodes(pNode2, pNode3); 63 | ConnectListNodes(pNode3, pNode4); 64 | ConnectListNodes(pNode4, pNode5); 65 | 66 | Test(pNode1); 67 | 68 | DestroyList(pNode1); 69 | } 70 | 71 | // Only one node: 1 72 | void Test2() 73 | { 74 | printf("\nTest2 begins.\n"); 75 | 76 | ListNode* pNode1 = CreateListNode(1); 77 | 78 | Test(pNode1); 79 | 80 | DestroyList(pNode1); 81 | } 82 | 83 | // Empty list 84 | void Test3() 85 | { 86 | printf("\nTest3 begins.\n"); 87 | 88 | Test(NULL); 89 | } 90 | 91 | int main(int argc, char* argv[]) 92 | { 93 | Test1(); 94 | Test2(); 95 | Test3(); 96 | 97 | return 0; 98 | } 99 | -------------------------------------------------------------------------------- /028_TurningNumber.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | public class TurningNumber { 5 | public static int getTurningIndex(int numbers[]) { 6 | if(numbers.length <= 2) 7 | return -1; 8 | 9 | int left = 0; 10 | int right = numbers.length - 1; 11 | while(right > left + 1) { 12 | int middle = (left + right) / 2; 13 | if(middle == 0 || middle == numbers.length - 1) 14 | return -1; 15 | 16 | if(numbers[middle] > numbers[middle - 1] 17 | && numbers[middle] > numbers[middle + 1]) 18 | return middle; 19 | else if(numbers[middle] > numbers[middle - 1] 20 | && numbers[middle] < numbers[middle + 1]) 21 | left = middle; 22 | else 23 | right = middle; 24 | } 25 | 26 | return -1; 27 | } 28 | 29 | //================= Test Code ================= 30 | private static void test(String testName, int[] numbers, int expected) { 31 | System.out.print(testName + " begins: "); 32 | 33 | if(getTurningIndex(numbers) == expected) 34 | System.out.print("passed.\n"); 35 | else 36 | System.out.print("FAILED.\n"); 37 | } 38 | 39 | private static void test1() { 40 | int numbers[] = {1, 2, 3, 4, 5, 10, 9, 8, 7, 6}; 41 | int expected = 5; 42 | test("test1", numbers, expected); 43 | } 44 | 45 | private static void test2() { 46 | int numbers[] = {1, 10, 9, 8, 7, 6, 5, 4, 3, 2}; 47 | int expected = 1; 48 | test("test2", numbers, expected); 49 | } 50 | 51 | private static void test3() { 52 | int numbers[] = {1, 2, 3, 4, 5, 6, 7, 8, 10, 9}; 53 | int expected = 8; 54 | test("test3", numbers, expected); 55 | } 56 | 57 | private static void test4() { 58 | int numbers[] = {1, 2, 1}; 59 | int expected = 1; 60 | test("test4", numbers, expected); 61 | } 62 | 63 | public static void main(String args[]) { 64 | test1(); 65 | test2(); 66 | test3(); 67 | test4(); 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /087_TwoNumbersWithSum.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | public class TwoNumbersWithSum { 5 | public static boolean hasPairWithSum(int numbers[], int sum) { 6 | boolean found = false; 7 | 8 | int ahead = numbers.length - 1; 9 | int behind = 0; 10 | 11 | while(ahead > behind) { 12 | int curSum = numbers[ahead] + numbers[behind]; 13 | 14 | if(curSum == sum) { 15 | found = true; 16 | break; 17 | } 18 | else if(curSum > sum) 19 | ahead --; 20 | else 21 | behind ++; 22 | } 23 | 24 | return found; 25 | } 26 | 27 | //================= Test Code ================= 28 | private static void test(String testName, int numbers[], int sum, boolean expected) { 29 | System.out.print(testName + " Begins: "); 30 | 31 | if(hasPairWithSum(numbers, sum) == expected) 32 | System.out.println("Passed."); 33 | else 34 | System.out.println("FAILED."); 35 | } 36 | 37 | // The array has two numbers with the given sum, 38 | // and two numbers are inside the array 39 | private static void test1() { 40 | int numbers[] = {1, 2, 4, 7, 11, 15}; 41 | test("test1", numbers, 15, true); 42 | } 43 | 44 | // The array has two numbers with the given sum, 45 | // and two numbers are the first and last elements 46 | private static void test2() { 47 | int numbers[] = {1, 2, 4, 7, 11, 16}; 48 | test("test2", numbers, 17, true); 49 | } 50 | 51 | // The array does not have two numbers with the given sum 52 | private static void test3() { 53 | int numbers[] = {1, 2, 4, 7, 11, 16}; 54 | test("test3", numbers, 10, false); 55 | } 56 | 57 | // There is only one number in the array 58 | private static void test4() { 59 | int numbers[] = {2}; 60 | test("test4", numbers, 2, false); 61 | } 62 | 63 | public static void main(String[] args) { 64 | test1(); 65 | test2(); 66 | test3(); 67 | test4(); 68 | } 69 | 70 | } 71 | -------------------------------------------------------------------------------- /077_FirstCharAppearingOnce.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | using namespace std; 8 | 9 | class CharStatistics 10 | { 11 | public: 12 | CharStatistics() : index (0) 13 | { 14 | for(int i = 0; i < 256; ++i) 15 | occurrence[i] = -1; 16 | } 17 | 18 | void Insert(char ch) 19 | { 20 | if(occurrence[ch] == -1) 21 | occurrence[ch] = index; 22 | else if(occurrence[ch] >= 0) 23 | occurrence[ch] = -2; 24 | 25 | index++; 26 | } 27 | 28 | char FirstAppearingOnce() 29 | { 30 | char ch = '\0'; 31 | int minIndex = numeric_limits::max(); 32 | for(int i = 0; i < 256; ++i) 33 | { 34 | if(occurrence[i] >= 0 && occurrence[i] < minIndex) 35 | { 36 | ch = (char)i; 37 | minIndex = occurrence[i]; 38 | } 39 | } 40 | 41 | return ch; 42 | } 43 | 44 | private: 45 | // occurrence[i]: A character with ASCII value i; 46 | // occurrence[i] = -1: The character has not found; 47 | // occurrence[i] = -2: The character has been found for mutlple times 48 | // occurrence[i] >= 0: The character has been found only once 49 | int occurrence[256]; 50 | int index; 51 | }; 52 | 53 | void Test(char* testName, CharStatistics chars, char expected) 54 | { 55 | if(testName != NULL) 56 | printf("%s begins: ", testName); 57 | 58 | if(chars.FirstAppearingOnce() == expected) 59 | printf("Passed.\n"); 60 | else 61 | printf("FAILED.\n"); 62 | } 63 | 64 | int main(int argc, char* argv[]) 65 | { 66 | CharStatistics chars; 67 | 68 | Test("Test1", chars, '\0'); 69 | 70 | chars.Insert('g'); 71 | Test("Test2", chars, 'g'); 72 | 73 | chars.Insert('o'); 74 | Test("Test3", chars, 'g'); 75 | 76 | chars.Insert('o'); 77 | Test("Test4", chars, 'g'); 78 | 79 | chars.Insert('g'); 80 | Test("Test5", chars, '\0'); 81 | 82 | chars.Insert('l'); 83 | Test("Test6", chars, 'l'); 84 | 85 | chars.Insert('e'); 86 | Test("Test7", chars, 'l'); 87 | 88 | return 0; 89 | } 90 | -------------------------------------------------------------------------------- /001_PalindromeNumber.c: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | // ==================== Solution 1 ==================== 8 | 9 | int IsPalindrome(const char* const string) 10 | { 11 | int palindrome = 1; 12 | if(string != NULL) 13 | { 14 | int length = strlen(string); 15 | int half = length >> 1; 16 | 17 | int i; 18 | for(i = 0; i < half; ++ i) 19 | { 20 | if(string[i] != string[length - 1 - i]) 21 | { 22 | palindrome = 0; 23 | break; 24 | } 25 | } 26 | } 27 | 28 | return palindrome; 29 | } 30 | 31 | /* It returns 1 when number is palindrome, otherwise returns 0. */ 32 | #define NUMBER_LENGTH 20 33 | int IsPalindrome_solution1(unsigned int number) 34 | { 35 | char string[NUMBER_LENGTH]; 36 | sprintf(string, "%d", number); 37 | 38 | return IsPalindrome(string); 39 | } 40 | 41 | // ==================== Solution 2 ==================== 42 | 43 | /* It returns 1 when number is palindrome, otherwise returns 0. */ 44 | int IsPalindrome_solution2(unsigned int number) 45 | { 46 | int reversed = 0; 47 | int copy = number; 48 | 49 | while(number != 0) 50 | { 51 | reversed = reversed * 10 + number % 10; 52 | number /= 10; 53 | } 54 | 55 | return (reversed == copy) ? 1 : 0; 56 | } 57 | 58 | // ==================== Test Code ==================== 59 | 60 | void Test(char* testName, int number, int expected) 61 | { 62 | if(testName != NULL) 63 | printf("%s begins: ", testName); 64 | 65 | if(IsPalindrome_solution1(number) == expected) 66 | printf("solution 1 passed; "); 67 | else 68 | printf("solution 1 FAILED; "); 69 | 70 | if(IsPalindrome_solution2(number) == expected) 71 | printf("solution 2 passed.\n"); 72 | else 73 | printf("solution 2 FAILED.\n"); 74 | } 75 | 76 | int main(int argc, char* argv[]) 77 | { 78 | Test("Test1", 5, 1); 79 | Test("Test2", 33, 1); 80 | Test("Test3", 242, 1); 81 | Test("Test4", 2332, 1); 82 | 83 | Test("Test5", 0, 1); 84 | 85 | Test("Test6", 32, 0); 86 | Test("Test7", 233, 0); 87 | Test("Test8", 2331, 0); 88 | Test("Test9", 2322, 0); 89 | 90 | return 0; 91 | } 92 | -------------------------------------------------------------------------------- /074_SortArrayForMinNumber.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | import java.util.Arrays; 5 | import java.util.Comparator; 6 | 7 | public class SortArrayForMinNumber { 8 | public static void PrintMinNumber(int numbers[]) { 9 | String strNumbers[] = new String[numbers.length]; 10 | for(int i = 0; i < numbers.length; ++i) { 11 | strNumbers[i] = String.valueOf(numbers[i]); 12 | } 13 | 14 | Arrays.sort(strNumbers, (new SortArrayForMinNumber()).new NumericComparator()); 15 | 16 | for(int i = 0; i < numbers.length; ++i) 17 | System.out.print(strNumbers[i]); 18 | System.out.print("\n"); 19 | } 20 | 21 | public class NumericComparator implements Comparator{ 22 | public int compare(String num1, String num2) { 23 | String str1 = num1 + num2; 24 | String str2 = num2 + num1; 25 | return str1.compareTo(str2); 26 | } 27 | } 28 | 29 | // ====================Test code==================== 30 | private static void Test(String testName, int numbers[], String expectedResult) 31 | { 32 | System.out.println(testName + " begins:"); 33 | 34 | System.out.println("Expected result is: \t" + expectedResult); 35 | 36 | System.out.print("Actual result is: \t"); 37 | PrintMinNumber(numbers); 38 | 39 | System.out.print("\n"); 40 | } 41 | 42 | private static void Test1() { 43 | int numbers[] = {3, 5, 1, 4, 2}; 44 | Test("Test1", numbers, "12345"); 45 | } 46 | 47 | private static void Test2() { 48 | int numbers[] = {3, 32, 321}; 49 | Test("Test2", numbers, "321323"); 50 | } 51 | 52 | private static void Test3() { 53 | int numbers[] = {3, 323, 32123}; 54 | Test("Test3", numbers, "321233233"); 55 | } 56 | 57 | private static void Test4() { 58 | int numbers[] = {1, 11, 111}; 59 | Test("Test4", numbers, "111111"); 60 | } 61 | 62 | // There is only one element in an array 63 | private static void Test5(){ 64 | int numbers[] = {321}; 65 | Test("Test5", numbers, "321"); 66 | } 67 | 68 | public static void main(String[] args) { 69 | Test1(); 70 | Test2(); 71 | Test3(); 72 | Test4(); 73 | Test5(); 74 | } 75 | } 76 | -------------------------------------------------------------------------------- /021_QueueWithTwoStacks.cs: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | using System; 5 | using System.Collections.Generic; 6 | 7 | namespace QueueWithStacks 8 | { 9 | public class QueueWithTwoStacks 10 | { 11 | public void Enqueue(T item) 12 | { 13 | stack1.Push(item); 14 | } 15 | 16 | public T Dequeue() 17 | { 18 | if (stack2.Count == 0) 19 | { 20 | while (stack1.Count > 0) 21 | { 22 | T item = stack1.Peek(); 23 | stack1.Pop(); 24 | stack2.Push(item); 25 | } 26 | } 27 | 28 | if (stack2.Count == 0) 29 | throw new InvalidOperationException("Queue is Empty"); 30 | 31 | T head = stack2.Peek(); 32 | stack2.Pop(); 33 | 34 | return head; 35 | } 36 | 37 | private Stack stack1 = new Stack(); 38 | private Stack stack2 = new Stack(); 39 | } 40 | 41 | class Program 42 | { 43 | static void Test(char actual, char expected) 44 | { 45 | if (actual == expected) 46 | Console.WriteLine("Test passed."); 47 | else 48 | Console.WriteLine("Test failed."); 49 | } 50 | 51 | static void Main(string[] args) 52 | { 53 | QueueWithTwoStacks queue = new QueueWithTwoStacks(); 54 | 55 | queue.Enqueue('a'); 56 | queue.Enqueue('b'); 57 | queue.Enqueue('c'); 58 | 59 | char head = queue.Dequeue(); 60 | Test(head, 'a'); 61 | 62 | head = queue.Dequeue(); 63 | Test(head, 'b'); 64 | 65 | queue.Enqueue('d'); 66 | head = queue.Dequeue(); 67 | Test(head, 'c'); 68 | 69 | queue.Enqueue('e'); 70 | head = queue.Dequeue(); 71 | Test(head, 'd'); 72 | 73 | head = queue.Dequeue(); 74 | Test(head, 'e'); 75 | 76 | try 77 | { 78 | head = queue.Dequeue(); 79 | Console.WriteLine("Test failed."); 80 | } 81 | catch(InvalidOperationException) 82 | { 83 | Console.WriteLine("Test passed."); 84 | } 85 | } 86 | } 87 | } 88 | -------------------------------------------------------------------------------- /040_Power.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | #include 7 | 8 | bool Equal(double num1, double num2); 9 | double PowerWithUnsignedExponent(double base, unsigned int exponent); 10 | 11 | double Power(double base, int exponent) 12 | { 13 | errno = 0; 14 | 15 | if(Equal(base, 0.0) && exponent < 0) 16 | { 17 | errno = EDOM; 18 | return 0.0; 19 | } 20 | 21 | unsigned int absExponent = (unsigned int)(exponent); 22 | if(exponent < 0) 23 | absExponent = (unsigned int)(-exponent); 24 | 25 | double result = PowerWithUnsignedExponent(base, absExponent); 26 | if(exponent < 0) 27 | result = 1.0 / result; 28 | 29 | return result; 30 | } 31 | 32 | /* 33 | double PowerWithUnsignedExponent(double base, unsigned int exponent) 34 | { 35 | double result = 1.0; 36 | 37 | for(int i = 1; i <= exponent; ++i) 38 | result *= base; 39 | 40 | return result; 41 | } 42 | */ 43 | double PowerWithUnsignedExponent(double base, unsigned int exponent) 44 | { 45 | if(exponent == 0) 46 | return 1; 47 | if(exponent == 1) 48 | return base; 49 | 50 | double result = PowerWithUnsignedExponent(base, exponent >> 1); 51 | result *= result; 52 | if((exponent & 0x1) == 1) 53 | result *= base; 54 | 55 | return result; 56 | } 57 | 58 | bool Equal(double num1, double num2) 59 | { 60 | if((num1 - num2 > -0.0000001) 61 | && (num1 - num2 < 0.0000001)) 62 | return true; 63 | else 64 | return false; 65 | } 66 | 67 | // ==================== Test Code ==================== 68 | void Test(char* testName, double base, int exponent, double expectedResult, int expectedFlag) 69 | { 70 | if(testName != NULL) 71 | printf("%s begins: ", testName); 72 | 73 | double result = Power(base, exponent); 74 | if(abs(result - expectedResult) < 0.00000001 && errno == expectedFlag) 75 | printf("Test passed.\n"); 76 | else 77 | printf("Test failed.\n"); 78 | } 79 | 80 | int main(int argc, char* argv[]) 81 | { 82 | Test("Test1", 2, 3, 8, 0); 83 | 84 | Test("Test2", -2, 3, -8, 0); 85 | 86 | Test("Test3", 2, -3, 0.125, 0); 87 | 88 | Test("Test4", 2, 0, 1, 0); 89 | 90 | Test("Test5", 0, 0, 1, 0); 91 | 92 | Test("Test6", 0, 4, 0, 0); 93 | 94 | Test("Test7", 0, -4, 0, EDOM); 95 | 96 | return 0; 97 | } 98 | -------------------------------------------------------------------------------- /005_Duplication.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | 5 | public class Duplication { 6 | public static int duplicate(int numbers[]) { 7 | int length = numbers.length; 8 | 9 | int sum1 = 0; 10 | for(int i = 0; i < length; ++i) { 11 | if(numbers[i] < 0 || numbers[i] > length - 2) 12 | throw new IllegalArgumentException("Invalid numbers."); 13 | 14 | sum1 += numbers[i]; 15 | } 16 | 17 | int sum2 = ((length - 1) * (length - 2)) >> 1; 18 | 19 | return sum1 - sum2; 20 | } 21 | 22 | //================= Test Code ================= 23 | private static void test(String testName, int numbers[], int expected, boolean invalidArgument){ 24 | System.out.print(testName + " begins: "); 25 | 26 | try { 27 | int duplication = duplicate(numbers); 28 | 29 | if(!invalidArgument && duplication == expected) 30 | System.out.print("Passed.\n"); 31 | else 32 | System.out.print("FAILED.\n"); 33 | } 34 | catch(IllegalArgumentException e){ 35 | if(invalidArgument) 36 | System.out.print("Passed.\n"); 37 | else 38 | System.out.print("FAILED.\n"); 39 | } 40 | } 41 | 42 | private static void test1(){ 43 | int numbers[] = {2, 1, 3, 1, 0}; 44 | test("Test1", numbers, 1, false); 45 | } 46 | 47 | private static void test2(){ 48 | int numbers[] = {2, 0, 3, 1, 0}; 49 | test("Test2", numbers, 0, false); 50 | } 51 | 52 | private static void test3(){ 53 | int numbers[] = {2, 0, 4, 3, 1, 4}; 54 | test("Test3", numbers, 4, false); 55 | } 56 | 57 | private static void test4(){ 58 | int numbers[] = {2, 1, 3, 0, 4}; 59 | test("Test4", numbers, 0, true); 60 | } 61 | 62 | private static void test5(){ 63 | int numbers[] = {2, 1, 3, 0, -1}; 64 | test("Test5", numbers, 0, true); 65 | } 66 | 67 | private static void test6(){ 68 | int numbers[] = {0}; 69 | test("Test6", numbers, 0, true); 70 | } 71 | 72 | public static void main(String[] args) { 73 | test1(); 74 | test2(); 75 | test3(); 76 | test4(); 77 | test5(); 78 | test6(); 79 | } 80 | } 81 | -------------------------------------------------------------------------------- /080_Anagram.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | import java.util.HashMap; 5 | import java.util.Map; 6 | 7 | 8 | public class Anagram { 9 | public static boolean areAnagrams(String str1, String str2){ 10 | if(str1.length() != str2.length()) 11 | return false; 12 | 13 | Map times = new HashMap(); 14 | for(int i = 0; i < str1.length(); ++i){ 15 | Character ch = str1.charAt(i); 16 | if(times.containsKey(ch)) 17 | times.put(ch, times.get(ch) + 1); 18 | else 19 | times.put(ch, 1); 20 | } 21 | 22 | for(int i = 0; i < str2.length(); ++i){ 23 | Character ch = str2.charAt(i); 24 | if(!times.containsKey(ch)) 25 | return false; 26 | 27 | if(times.get(ch) == 0) 28 | return false; 29 | 30 | times.put(ch, times.get(ch) - 1); 31 | } 32 | 33 | // If two strings with same length and containing 34 | // same set of characters are not anagrams, 35 | // it returns false before, because values of some 36 | // characters reach 0 in the second for loop above. 37 | // Therefore, it is safe to return true here. 38 | return true; 39 | } 40 | 41 | //================= Test Code ================= 42 | private static void test(String testName, String str1, String str2, boolean expected){ 43 | System.out.print(testName + " begins: "); 44 | 45 | if(areAnagrams(str1, str2) == expected) 46 | System.out.print("passed.\n"); 47 | else 48 | System.out.print("FAILED.\n"); 49 | } 50 | 51 | private static void test1(){ 52 | test("Test1", "silent", "listen", true); 53 | } 54 | 55 | private static void test2(){ 56 | test("Test2", "evil", "live", true); 57 | } 58 | 59 | private static void test3(){ 60 | test("Test3", "eleven plus two", "twelve plus one", true); 61 | } 62 | 63 | private static void test4(){ 64 | test("Test4", "there", "their", false); 65 | } 66 | 67 | private static void test5(){ 68 | test("Test5", "an", "and", false); 69 | } 70 | 71 | static public void main(String[] args) { 72 | test1(); 73 | test2(); 74 | test3(); 75 | test4(); 76 | test5(); 77 | } 78 | } 79 | -------------------------------------------------------------------------------- /068_StringCombination.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | import java.util.BitSet; 5 | import java.util.Stack; 6 | 7 | public class StringCombination { 8 | // ==================== solution 1 ==================== 9 | public static void combination_solution1(String str) { 10 | Stack result = new Stack(); 11 | for(int i = 1; i <= str.length(); ++ i) { 12 | combination(str, 0, i, result); 13 | } 14 | } 15 | 16 | private static void combination(String str, int index, int number, Stack result) { 17 | if(number == 0) { 18 | System.out.println(result); 19 | return; 20 | } 21 | 22 | if(index == str.length()) 23 | return; 24 | 25 | // select the character str[index] 26 | result.push(str.charAt(index)); 27 | combination(str, index + 1, number - 1, result); 28 | result.pop(); 29 | 30 | // ignore the character str[index] 31 | combination(str, index + 1, number, result); 32 | } 33 | 34 | // ==================== solution 2 ==================== 35 | public static void combination_solution2(String str) { 36 | BitSet bits = new BitSet(str.length()); 37 | while(increment(bits, str.length())) 38 | print(str, bits); 39 | } 40 | 41 | private static boolean increment(BitSet bits, int length) { 42 | int index = length - 1; 43 | 44 | while(index >= 0 && bits.get(index)) { 45 | bits.clear(index); 46 | --index; 47 | } 48 | 49 | if(index < 0) 50 | return false; 51 | 52 | bits.set(index); 53 | return true; 54 | } 55 | 56 | private static void print(String str, BitSet bits) { 57 | for(int i = 0; i < str.length(); ++i) { 58 | if(bits.get(i)) 59 | System.out.print(str.charAt(i)); 60 | } 61 | 62 | System.out.println(); 63 | } 64 | 65 | // ==================== test code ==================== 66 | private static void test(String str) { 67 | System.out.println("Test Begins for " + str); 68 | combination_solution1(str); 69 | combination_solution2(str); 70 | } 71 | 72 | public static void main(String args[]) { 73 | test(""); 74 | test("a"); 75 | test("ab"); 76 | test("abc"); 77 | test("abcd"); 78 | } 79 | } 80 | -------------------------------------------------------------------------------- /022_StackWithTwoQueues.cs: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | using System; 5 | using System.Collections.Generic; 6 | 7 | namespace StackWithQueues 8 | { 9 | public class StackWithTwoQueues 10 | { 11 | public void Push(T item) 12 | { 13 | if (queue2.Count != 0) 14 | queue2.Enqueue(item); 15 | else 16 | queue1.Enqueue(item); 17 | } 18 | 19 | public T Pop() 20 | { 21 | if (queue1.Count == 0 && queue2.Count == 0) 22 | throw new InvalidOperationException("Stack is Empty"); 23 | 24 | Queue emptyQueue = queue1; 25 | Queue nonemptyQueue = queue2; 26 | if (queue1.Count > 0) 27 | { 28 | emptyQueue = queue2; 29 | nonemptyQueue = queue1; 30 | } 31 | 32 | while (nonemptyQueue.Count > 1) 33 | emptyQueue.Enqueue(nonemptyQueue.Dequeue()); 34 | 35 | return nonemptyQueue.Dequeue(); 36 | } 37 | 38 | private Queue queue1 = new Queue(); 39 | private Queue queue2 = new Queue(); 40 | } 41 | 42 | class Program 43 | { 44 | static void Test(char actual, char expected) 45 | { 46 | if (actual == expected) 47 | Console.WriteLine("Test passed."); 48 | else 49 | Console.WriteLine("Test failed."); 50 | } 51 | 52 | static void Main(string[] args) 53 | { 54 | StackWithTwoQueues stack = new StackWithTwoQueues(); 55 | stack.Push('a'); 56 | stack.Push('b'); 57 | stack.Push('c'); 58 | 59 | char top = stack.Pop(); 60 | Test(top, 'c'); 61 | 62 | top = stack.Pop(); 63 | Test(top, 'b'); 64 | 65 | stack.Push('d'); 66 | top = stack.Pop(); 67 | Test(top, 'd'); 68 | 69 | top = stack.Pop(); 70 | Test(top, 'a'); 71 | 72 | try 73 | { 74 | top = stack.Pop(); 75 | Console.WriteLine("Test failed."); 76 | } 77 | catch (InvalidOperationException) 78 | { 79 | Console.WriteLine("Test passed."); 80 | } 81 | 82 | stack.Push('e'); 83 | stack.Push('f'); 84 | 85 | top = stack.Pop(); 86 | Test(top, 'f'); 87 | 88 | top = stack.Pop(); 89 | Test(top, 'e'); 90 | } 91 | } 92 | } 93 | -------------------------------------------------------------------------------- /096_LastNumberInCircle.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | using namespace std; 8 | 9 | // ==================== Solution 1==================== 10 | int LastRemaining_Solution1(unsigned int n, unsigned int m) 11 | { 12 | if(n < 1 || m < 1) 13 | return -1; 14 | 15 | list numbers; 16 | for(unsigned int i = 0; i < n; ++ i) 17 | numbers.push_back(i); 18 | 19 | list::iterator current = numbers.begin(); 20 | while(numbers.size() > 1) 21 | { 22 | for(int i = 1; i < m; ++ i) 23 | { 24 | current ++; 25 | if(current == numbers.end()) 26 | current = numbers.begin(); 27 | } 28 | 29 | list::iterator next = ++ current; 30 | if(next == numbers.end()) 31 | next = numbers.begin(); 32 | 33 | -- current; 34 | numbers.erase(current); 35 | current = next; 36 | } 37 | 38 | return *(current); 39 | } 40 | 41 | // ==================== Solution 2 ==================== 42 | int LastRemaining_Solution2(unsigned int n, unsigned int m) 43 | { 44 | if(n < 1 || m < 1) 45 | return -1; 46 | 47 | int last = 0; 48 | for (int i = 2; i <= n; i ++) 49 | last = (last + m) % i; 50 | 51 | return last; 52 | } 53 | 54 | // ==================== Test Code ==================== 55 | void Test(char* testName, unsigned int n, unsigned int m, int expected) 56 | { 57 | if(testName != NULL) 58 | printf("%s begins: \n", testName); 59 | 60 | if(LastRemaining_Solution1(n, m) == expected) 61 | printf("Solution1 passed.\n"); 62 | else 63 | printf("Solution1 failed.\n"); 64 | 65 | if(LastRemaining_Solution2(n, m) == expected) 66 | printf("Solution2 passed.\n"); 67 | else 68 | printf("Solution2 failed.\n"); 69 | 70 | printf("\n"); 71 | } 72 | 73 | void Test1() 74 | { 75 | Test("Test1", 5, 3, 3); 76 | } 77 | 78 | void Test2() 79 | { 80 | Test("Test2", 5, 2, 2); 81 | } 82 | 83 | void Test3() 84 | { 85 | Test("Test3", 6, 7, 4); 86 | } 87 | 88 | void Test4() 89 | { 90 | Test("Test4", 6, 6, 3); 91 | } 92 | 93 | void Test5() 94 | { 95 | Test("Test5", 0, 0, -1); 96 | } 97 | 98 | void Test6() 99 | { 100 | Test("Test6", 4000, 997, 1027); 101 | } 102 | 103 | int main(int argc, char* argv[]) 104 | { 105 | Test1(); 106 | Test2(); 107 | Test3(); 108 | Test4(); 109 | Test5(); 110 | Test6(); 111 | 112 | return 0; 113 | } 114 | 115 | -------------------------------------------------------------------------------- /106_StringToInt.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | long long StrToIntCore(const char* str, bool minus); 8 | 9 | enum Status {kValid = 0, kInvalid}; 10 | int g_nStatus = kValid; 11 | 12 | int StrToInt(const char* str) 13 | { 14 | g_nStatus = kInvalid; 15 | long long num = 0; 16 | 17 | if(str != NULL && *str != '\0') 18 | { 19 | bool minus = false; 20 | if(*str == '+') 21 | str ++; 22 | else if(*str == '-') 23 | { 24 | str ++; 25 | minus = true; 26 | } 27 | 28 | if(*str != '\0') 29 | { 30 | num = StrToIntCore(str, minus); 31 | } 32 | } 33 | 34 | return (int)num; 35 | } 36 | 37 | long long StrToIntCore(const char* digit, bool minus) 38 | { 39 | long long num = 0; 40 | 41 | while(*digit != '\0') 42 | { 43 | if(*digit >= '0' && *digit <= '9') 44 | { 45 | int flag = minus ? -1 : 1; 46 | num = num * 10 + flag * (*digit - '0'); 47 | 48 | if((!minus && num > 0x7FFFFFFF) 49 | || (minus && num < (signed int)0x80000000)) 50 | { 51 | num = 0; 52 | break; 53 | } 54 | 55 | digit++; 56 | } 57 | else 58 | { 59 | num = 0; 60 | break; 61 | } 62 | } 63 | 64 | if(*digit == '\0') 65 | { 66 | g_nStatus = kValid; 67 | } 68 | 69 | return num; 70 | } 71 | 72 | // ==================== Test Code ==================== 73 | void Test(char* string) 74 | { 75 | int result = StrToInt(string); 76 | if(result == 0 && g_nStatus == kInvalid) 77 | printf("the input %s is invalid.\n", string); 78 | else 79 | printf("number for %s is: %d.\n", string, result); 80 | } 81 | 82 | int main(int argc, char* argv[]) 83 | { 84 | Test(NULL); 85 | 86 | Test(""); 87 | 88 | Test("123"); 89 | 90 | Test("+123"); 91 | 92 | Test("-123"); 93 | 94 | Test("1a33"); 95 | 96 | Test("+0"); 97 | 98 | Test("-0"); 99 | 100 | //Maximal positive integer, 0x7FFFFFFF 101 | Test("+2147483647"); 102 | 103 | Test("-2147483647"); 104 | 105 | Test("+2147483648"); 106 | 107 | //Minimal negative integer, 0x80000000 108 | Test("-2147483648"); 109 | 110 | Test("+2147483649"); 111 | 112 | Test("-2147483649"); 113 | 114 | Test("+"); 115 | 116 | Test("-"); 117 | 118 | return 0; 119 | } 120 | -------------------------------------------------------------------------------- /Utility/list.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include "list.h" 4 | 5 | ListNode* CreateListNode(int value) 6 | { 7 | ListNode* pNode = new ListNode(); 8 | pNode->m_nValue = value; 9 | pNode->m_pNext = NULL; 10 | 11 | return pNode; 12 | } 13 | 14 | void ConnectListNodes(ListNode* pCurrent, ListNode* pNext) 15 | { 16 | if(pCurrent == NULL) 17 | { 18 | printf("Error to connect two nodes.\n"); 19 | exit(1); 20 | } 21 | 22 | pCurrent->m_pNext = pNext; 23 | } 24 | 25 | void PrintListNode(ListNode* pNode) 26 | { 27 | if(pNode == NULL) 28 | { 29 | printf("The node is NULL\n"); 30 | } 31 | else 32 | { 33 | printf("The key in node is %d.\n", pNode->m_nValue); 34 | } 35 | } 36 | 37 | void PrintList(ListNode* pHead) 38 | { 39 | printf("PrintList starts.\n"); 40 | 41 | ListNode* pNode = pHead; 42 | while(pNode != NULL) 43 | { 44 | printf("%d\t", pNode->m_nValue); 45 | pNode = pNode->m_pNext; 46 | } 47 | 48 | printf("\nPrintList ends.\n"); 49 | } 50 | 51 | void DestroyList(ListNode* pHead) 52 | { 53 | ListNode* pNode = pHead; 54 | while(pNode != NULL) 55 | { 56 | pHead = pHead->m_pNext; 57 | delete pNode; 58 | pNode = pHead; 59 | } 60 | } 61 | 62 | void AddToTail(ListNode** pHead, int value) 63 | { 64 | ListNode* pNew = new ListNode(); 65 | pNew->m_nValue = value; 66 | pNew->m_pNext = NULL; 67 | 68 | if(*pHead == NULL) 69 | { 70 | *pHead = pNew; 71 | } 72 | else 73 | { 74 | ListNode* pNode = *pHead; 75 | while(pNode->m_pNext != NULL) 76 | pNode = pNode->m_pNext; 77 | 78 | pNode->m_pNext = pNew; 79 | } 80 | } 81 | 82 | void RemoveNode(ListNode** pHead, int value) 83 | { 84 | if(pHead == NULL || *pHead == NULL) 85 | return; 86 | 87 | ListNode* pToBeDeleted = NULL; 88 | if((*pHead)->m_nValue == value) 89 | { 90 | pToBeDeleted = *pHead; 91 | *pHead = (*pHead)->m_pNext; 92 | } 93 | else 94 | { 95 | ListNode* pNode = *pHead; 96 | while(pNode->m_pNext != NULL && pNode->m_pNext->m_nValue != value) 97 | pNode = pNode->m_pNext; 98 | 99 | if(pNode->m_pNext != NULL && pNode->m_pNext->m_nValue == value) 100 | { 101 | pToBeDeleted = pNode->m_pNext; 102 | pNode->m_pNext = pNode->m_pNext->m_pNext; 103 | } 104 | } 105 | 106 | if(pToBeDeleted != NULL) 107 | { 108 | delete pToBeDeleted; 109 | pToBeDeleted = NULL; 110 | } 111 | } -------------------------------------------------------------------------------- /012_NumericStrings.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | 6 | void scanDigits(char** string); 7 | bool isExponential(char** string); 8 | 9 | bool isNumeric(char* string) 10 | { 11 | if(string == NULL) 12 | return false; 13 | 14 | if(*string == '+' || *string == '-') 15 | ++string; 16 | if(*string == '\0') 17 | return false; 18 | 19 | bool numeric = true; 20 | 21 | scanDigits(&string); 22 | if(*string != '\0') 23 | { 24 | // for floats 25 | if(*string == '.') 26 | { 27 | ++string; 28 | scanDigits(&string); 29 | 30 | if(*string == 'e' || *string == 'E') 31 | numeric = isExponential(&string); 32 | } 33 | // for integers 34 | else if(*string == 'e' || *string == 'E') 35 | numeric = isExponential(&string); 36 | else 37 | numeric = false; 38 | } 39 | 40 | return numeric && *string == '\0'; 41 | } 42 | 43 | void scanDigits(char** string) 44 | { 45 | while(**string != '\0' && **string >= '0' && **string <= '9') 46 | ++(*string); 47 | } 48 | 49 | bool isExponential(char** string) 50 | { 51 | if(**string != 'e' && **string != 'E') 52 | return false; 53 | 54 | ++(*string); 55 | if(**string == '+' || **string == '-') 56 | ++(*string); 57 | 58 | if(**string == '\0') 59 | return false; 60 | 61 | scanDigits(string); 62 | return (**string == '\0') ? true : false; 63 | } 64 | 65 | // ==================== Test Code ==================== 66 | 67 | void Test(char* testName, char* string, bool expected) 68 | { 69 | if(testName != NULL) 70 | printf("%s begins: ", testName); 71 | 72 | if(isNumeric(string) == expected) 73 | printf("Passed.\n"); 74 | else 75 | printf("FAILED.\n"); 76 | } 77 | 78 | int main(int argc, char* argv[]) 79 | { 80 | Test("Test1", "100", true); 81 | Test("Test2", "123.45e+6", true); 82 | Test("Test3", "+500", true); 83 | Test("Test4", "5e2", true); 84 | Test("Test5", "3.1416", true); 85 | Test("Test6", "600.", true); 86 | Test("Test7", "-.123", true); 87 | Test("Test8", "-1E-16", true); 88 | Test("Test9", "1.79769313486232E+308", true); 89 | 90 | printf("\n\n"); 91 | 92 | Test("Test10", "12e", false); 93 | Test("Test11", "1a3.14", false); 94 | Test("Test12", "1+23", false); 95 | Test("Test13", "1.2.3", false); 96 | Test("Test14", "+-5", false); 97 | Test("Test15", "12e+5.4", false); 98 | 99 | return 0; 100 | } 101 | 102 | -------------------------------------------------------------------------------- /091_ReverseWordsInSentence.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | void Reverse(char *pBegin, char *pEnd) 8 | { 9 | if(pBegin == NULL || pEnd == NULL) 10 | return; 11 | 12 | while(pBegin < pEnd) 13 | { 14 | char temp = *pBegin; 15 | *pBegin = *pEnd; 16 | *pEnd = temp; 17 | 18 | pBegin ++, pEnd --; 19 | } 20 | } 21 | 22 | char* ReverseSentence(char *pData) 23 | { 24 | if(pData == NULL) 25 | return NULL; 26 | 27 | char *pBegin = pData; 28 | 29 | char *pEnd = pData; 30 | while(*pEnd != '\0') 31 | pEnd ++; 32 | pEnd--; 33 | 34 | // Reverse the whole sentence 35 | Reverse(pBegin, pEnd); 36 | 37 | // Reverse every word in the sentence 38 | pBegin = pEnd = pData; 39 | while(*pBegin != '\0') 40 | { 41 | if(*pBegin == ' ') 42 | { 43 | pBegin ++; 44 | pEnd ++; 45 | } 46 | else if(*pEnd == ' ' || *pEnd == '\0') 47 | { 48 | Reverse(pBegin, --pEnd); 49 | pBegin = ++pEnd; 50 | } 51 | else 52 | { 53 | pEnd ++; 54 | } 55 | } 56 | 57 | return pData; 58 | } 59 | 60 | // ==================== Test Code ==================== 61 | void Test(char* testName, char* input, char* expectedResult) 62 | { 63 | if(testName != NULL) 64 | printf("%s begins: ", testName); 65 | 66 | ReverseSentence(input); 67 | 68 | if((input == NULL && expectedResult == NULL) 69 | || (input != NULL && strcmp(input, expectedResult) == 0)) 70 | printf("Passed.\n\n"); 71 | else 72 | printf("Failed.\n\n"); 73 | } 74 | 75 | // Multiple words 76 | void Test1() 77 | { 78 | char input[] = "I am a student."; 79 | char expected[] = "student. a am I"; 80 | 81 | Test("Test1", input, expected); 82 | } 83 | 84 | // Only one word 85 | void Test2() 86 | { 87 | char input[] = "Wonderful"; 88 | char expected[] = "Wonderful"; 89 | 90 | Test("Test2", input, expected); 91 | } 92 | 93 | // Null pointer 94 | void Test3() 95 | { 96 | Test("Test3", NULL, NULL); 97 | } 98 | 99 | // empty string 100 | void Test4() 101 | { 102 | Test("Test4", "", ""); 103 | } 104 | 105 | // Only blanks 106 | void Test5() 107 | { 108 | char input[] = " "; 109 | char expected[] = " "; 110 | Test("Test5", input, expected); 111 | } 112 | 113 | int main(int argc, char* argv[]) 114 | { 115 | Test1(); 116 | Test2(); 117 | Test3(); 118 | Test4(); 119 | Test5(); 120 | 121 | return 0; 122 | } 123 | 124 | -------------------------------------------------------------------------------- /027_ArrayRotation.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | public class Minimum { 5 | public static int getMin(int numbers[]) { 6 | int index1 = 0; 7 | int index2 = numbers.length - 1; 8 | int indexMid = index1; 9 | 10 | while(numbers[index1] >= numbers[index2]) { 11 | if(index2 - index1 == 1) { 12 | indexMid = index2; 13 | break; 14 | } 15 | 16 | indexMid = (index1 + index2) / 2; 17 | 18 | // if numbers with indexes index1, index2, indexMid 19 | // are equal, search sequentially 20 | if(numbers[index1] == numbers[index2] 21 | && numbers[indexMid] == numbers[index1]) 22 | return getMinSequentially(numbers, index1, index2); 23 | 24 | if(numbers[indexMid] >= numbers[index1]) 25 | index1 = indexMid; 26 | else if(numbers[indexMid] <= numbers[index2]) 27 | index2 = indexMid; 28 | 29 | } 30 | 31 | return numbers[indexMid]; 32 | } 33 | 34 | private static int getMinSequentially(int numbers[], int index1, int index2) { 35 | int result = numbers[index1]; 36 | for(int i = index1 + 1; i <= index2; ++i) { 37 | if(result > numbers[i]) 38 | result = numbers[i]; 39 | } 40 | 41 | return result; 42 | } 43 | 44 | 45 | //================= Test Code ================= 46 | private static void test(String testName, int[] numbers, int expected) { 47 | System.out.print(testName + " begins: "); 48 | 49 | if(getMin(numbers) == expected) 50 | System.out.print("passed.\n"); 51 | else 52 | System.out.print("FAILED.\n"); 53 | } 54 | 55 | public static void main(String argv[]) { 56 | // typical input, a rotation of a increasingly sorted array 57 | int array1[] = {3, 4, 5, 1, 2}; 58 | test("Test1", array1, 1); 59 | 60 | // duplicated number is the minimal 61 | int array2[] = {3, 4, 5, 1, 1, 2}; 62 | test("Test2", array2, 1); 63 | 64 | // duplicated number is not in both beginning and end 65 | int array3[] = {3, 4, 5, 1, 2, 2}; 66 | test("Test3", array3, 1); 67 | 68 | // duplicated number is in both beginning and end 69 | int array4[] = {1, 0, 1, 1, 1}; 70 | test("Test4", array4, 0); 71 | 72 | // rotate 0 numbers in an array 73 | int array5[] = {1, 2, 3, 4, 5}; 74 | test("Test5", array5, 1); 75 | 76 | // only one number in an array 77 | int array6[] = {2}; 78 | test("Test6", array6, 2); 79 | } 80 | } 81 | -------------------------------------------------------------------------------- /105_ConstuctArray.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | public class ConstuctArray { 5 | public static void multiply(double array1[], double array2[]){ 6 | if(array1.length == array2.length && array1.length > 0){ 7 | array2[0] = 1; 8 | for(int i = 1; i < array1.length; ++i){ 9 | array2[i] = array2[i - 1] * array1[i - 1]; 10 | } 11 | 12 | int temp = 1; 13 | for(int i = array1.length - 2; i >= 0; --i){ 14 | temp *= array1[i + 1]; 15 | array2[i] *= temp; 16 | } 17 | } 18 | } 19 | 20 | //================= Test Code ================= 21 | private static boolean equalArrays(double array1[], double array2[]){ 22 | if(array1.length != array2.length) 23 | return false; 24 | 25 | for(int i = 0; i < array1.length; ++i){ 26 | if(abs(array1[i] - array2[i]) > 0.0000001) 27 | return false; 28 | } 29 | 30 | return true; 31 | } 32 | 33 | private static double abs(double d) { 34 | return (d > 0) ? d : -d; 35 | } 36 | 37 | private static void test(String testName, double array1[], double array2[], double expected[]){ 38 | System.out.print(testName + " Begins: "); 39 | 40 | multiply(array1, array2); 41 | if(equalArrays(array2, expected)) 42 | System.out.println("Passed."); 43 | else 44 | System.out.println("FAILED."); 45 | } 46 | 47 | private static void test1(){ 48 | double array1[] = {1, 2, 3, 4, 5}; 49 | double array2[] = new double[5]; 50 | double expected[] = {120, 60, 40, 30, 24}; 51 | 52 | test("Test1", array1, array2, expected); 53 | } 54 | 55 | private static void test2(){ 56 | double array1[] = {1, 2, 0, 4, 5}; 57 | double array2[] = new double[5]; 58 | double expected[] = {0, 0, 40, 0, 0}; 59 | 60 | test("Test2", array1, array2, expected); 61 | } 62 | 63 | private static void test3(){ 64 | double array1[] = {1, 2, 0, 4, 0}; 65 | double array2[] = new double[5]; 66 | double expected[] = {0, 0, 0, 0, 0}; 67 | 68 | test("Test3", array1, array2, expected); 69 | } 70 | 71 | private static void test4(){ 72 | double array1[] = {1, -2, 3, -4, 5}; 73 | double array2[] = new double[5]; 74 | double expected[] = {120, -60, 40, -30, 24}; 75 | 76 | test("Test4", array1, array2, expected); 77 | } 78 | 79 | public static void main(String[] args){ 80 | test1(); 81 | test2(); 82 | test3(); 83 | test4(); 84 | } 85 | } 86 | -------------------------------------------------------------------------------- /092_LeftRotateString.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | void Reverse(char *pBegin, char *pEnd) 8 | { 9 | if(pBegin == NULL || pEnd == NULL) 10 | return; 11 | 12 | while(pBegin < pEnd) 13 | { 14 | char temp = *pBegin; 15 | *pBegin = *pEnd; 16 | *pEnd = temp; 17 | 18 | pBegin ++, pEnd --; 19 | } 20 | } 21 | 22 | char* LeftRotateString(char* pStr, int n) 23 | { 24 | if(pStr != NULL) 25 | { 26 | int nLength = static_cast(strlen(pStr)); 27 | if(nLength > 0 && n > 0 && n < nLength) 28 | { 29 | char* pFirstStart = pStr; 30 | char* pFirstEnd = pStr + n - 1; 31 | char* pSecondStart = pStr + n; 32 | char* pSecondEnd = pStr + nLength - 1; 33 | 34 | // Reverse the n leading characters 35 | Reverse(pFirstStart, pFirstEnd); 36 | // Reverse other characters 37 | Reverse(pSecondStart, pSecondEnd); 38 | // Reverse the whole string 39 | Reverse(pFirstStart, pSecondEnd); 40 | } 41 | } 42 | 43 | return pStr; 44 | } 45 | 46 | // ==================== Test Code ==================== 47 | void Test(char* testName, char* input, int num, char* expectedResult) 48 | { 49 | if(testName != NULL) 50 | printf("%s begins: ", testName); 51 | 52 | char* result = LeftRotateString(input, num); 53 | 54 | if((input == NULL && expectedResult == NULL) 55 | || (input != NULL && strcmp(result, expectedResult) == 0)) 56 | printf("Passed.\n\n"); 57 | else 58 | printf("Failed.\n\n"); 59 | } 60 | 61 | void Test1() 62 | { 63 | char input[] = "abcdefg"; 64 | char expected[] = "cdefgab"; 65 | 66 | Test("Test1", input, 2, expected); 67 | } 68 | 69 | void Test2() 70 | { 71 | char input[] = "abcdefg"; 72 | char expected[] = "bcdefga"; 73 | 74 | Test("Test2", input, 1, expected); 75 | } 76 | 77 | void Test3() 78 | { 79 | char input[] = "abcdefg"; 80 | char expected[] = "gabcdef"; 81 | 82 | Test("Test3", input, 6, expected); 83 | } 84 | 85 | void Test4() 86 | { 87 | Test("Test4", NULL, 6, NULL); 88 | } 89 | 90 | void Test5() 91 | { 92 | char input[] = "abcdefg"; 93 | char expected[] = "abcdefg"; 94 | 95 | Test("Test5", input, 0, expected); 96 | } 97 | 98 | void Test6() 99 | { 100 | char input[] = "abcdefg"; 101 | char expected[] = "abcdefg"; 102 | 103 | Test("Test6", input, 7, expected); 104 | } 105 | 106 | int main(int argc, char* argv[]) 107 | { 108 | Test1(); 109 | Test2(); 110 | Test3(); 111 | Test4(); 112 | Test5(); 113 | Test6(); 114 | 115 | return 0; 116 | } 117 | 118 | -------------------------------------------------------------------------------- /031_RobotMove.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | 6 | int getDigitSum(int number) 7 | { 8 | int sum = 0; 9 | while(number > 0) 10 | { 11 | sum += number % 10; 12 | number /= 10; 13 | } 14 | 15 | return sum; 16 | } 17 | 18 | bool check(int threshold, int rows, int cols, int row, int col, bool* visited) 19 | { 20 | if(row >=0 && row < rows && col >= 0 && col < cols 21 | && getDigitSum(row) + getDigitSum(col) <= threshold 22 | && !visited[row* cols + col]) 23 | return true; 24 | 25 | return false; 26 | } 27 | 28 | int movingCountCore(int threshold, int rows, int cols, int row, int col, bool* visited) 29 | { 30 | int count = 0; 31 | if(check(threshold, rows, cols, row, col, visited)) 32 | { 33 | visited[row * cols + col] = true; 34 | 35 | count = 1 + movingCountCore(threshold, rows, cols, row - 1, col, visited) 36 | + movingCountCore(threshold, rows, cols, row, col - 1, visited) 37 | + movingCountCore(threshold, rows, cols, row + 1, col, visited) 38 | + movingCountCore(threshold, rows, cols, row, col + 1, visited); 39 | } 40 | 41 | return count; 42 | } 43 | 44 | int movingCount(int threshold, int rows, int cols) 45 | { 46 | bool *visited = new bool[rows * cols]; 47 | for(int i = 0; i < rows * cols; ++i) 48 | visited[i] = false; 49 | 50 | int count = movingCountCore(threshold, rows, cols, 0, 0, visited); 51 | 52 | delete[] visited; 53 | 54 | return count; 55 | } 56 | 57 | // ================================ test code ================================ 58 | void test(char* testName, int threshold, int rows, int cols, int expected) 59 | { 60 | if(testName != NULL) 61 | printf("%s begins: ", testName); 62 | 63 | if(movingCount(threshold, rows, cols) == expected) 64 | printf("Passed.\n"); 65 | else 66 | printf("FAILED.\n"); 67 | } 68 | 69 | void test1() 70 | { 71 | test("Test1", 5, 10, 10, 21); 72 | } 73 | 74 | void test2() 75 | { 76 | test("Test2", 15, 20, 20, 359); 77 | } 78 | 79 | void test3() 80 | { 81 | test("Test3", 10, 1, 100, 29); 82 | } 83 | 84 | void test4() 85 | { 86 | test("Test4", 10, 1, 10, 10); 87 | } 88 | 89 | void test5() 90 | { 91 | test("Test5", 15, 100, 1, 79); 92 | } 93 | 94 | void test6() 95 | { 96 | test("Test6", 15, 10, 1, 10); 97 | } 98 | 99 | void test7() 100 | { 101 | test("Test7", 15, 1, 1, 1); 102 | } 103 | 104 | void test8() 105 | { 106 | test("Test8", -10, 10, 10, 0); 107 | } 108 | 109 | int main(int agrc, char* argv[]) 110 | { 111 | test1(); 112 | test2(); 113 | test3(); 114 | test4(); 115 | test5(); 116 | test6(); 117 | test7(); 118 | test8(); 119 | } -------------------------------------------------------------------------------- /041_Print1ToMaxOfNDigits.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | void PrintNumber(char* number); 8 | bool Increment(char* number, int length); 9 | void Print1ToMaxOfNDigitsCore(char* number, int length, int index); 10 | 11 | // ==================== Solution 1==================== 12 | void Print1ToMaxOfNDigits_1(int n) 13 | { 14 | if(n <= 0) 15 | return; 16 | 17 | char *number = new char[n + 1]; 18 | memset(number, '0', n); 19 | number[n] = '\0'; 20 | 21 | while(!Increment(number, n)) 22 | { 23 | PrintNumber(number); 24 | } 25 | 26 | delete []number; 27 | } 28 | 29 | bool Increment(char* number, int length) 30 | { 31 | bool isOverflow = false; 32 | int carry = 0; 33 | 34 | for(int i = length - 1; i >= 0; i --) 35 | { 36 | int sum = number[i] - '0' + carry; 37 | if(i == length - 1) 38 | sum ++; 39 | 40 | if(sum >= 10) 41 | { 42 | if(i == 0) 43 | isOverflow = true; 44 | else 45 | { 46 | sum -= 10; 47 | carry = 1; 48 | number[i] = '0' + sum; 49 | } 50 | } 51 | else 52 | { 53 | number[i] = '0' + sum; 54 | break; 55 | } 56 | } 57 | 58 | return isOverflow; 59 | } 60 | 61 | // ==================== Solution 2 ==================== 62 | void Print1ToMaxOfNDigits_2(int n) 63 | { 64 | if(n <= 0) 65 | return; 66 | 67 | char* number = new char[n + 1]; 68 | number[n] = '\0'; 69 | Print1ToMaxOfNDigitsCore(number, n, -1); 70 | 71 | delete[] number; 72 | } 73 | 74 | void Print1ToMaxOfNDigitsCore(char* number, int length, int index) 75 | { 76 | if(index == length - 1) 77 | { 78 | PrintNumber(number); 79 | return; 80 | } 81 | 82 | for(int i = 0; i < 10; ++i) 83 | { 84 | number[index + 1] = i + '0'; 85 | Print1ToMaxOfNDigitsCore(number, length, index + 1); 86 | } 87 | } 88 | 89 | // ==================== Common Function ==================== 90 | void PrintNumber(char* number) 91 | { 92 | char* pChar = number; 93 | while(*pChar == '0') 94 | ++pChar; 95 | 96 | if(*pChar != '\0') 97 | printf("%s\t", pChar); 98 | } 99 | 100 | // ==================== Test Code ==================== 101 | void Test(int n) 102 | { 103 | printf("Test for %d begins:\n", n); 104 | 105 | Print1ToMaxOfNDigits_1(n); 106 | printf("\n"); 107 | 108 | Print1ToMaxOfNDigits_2(n); 109 | printf("\n"); 110 | 111 | printf("Test for %d ends.\n", n); 112 | } 113 | 114 | int main(int argc, char* argv[]) 115 | { 116 | Test(1); 117 | Test(2); 118 | Test(3); 119 | Test(0); 120 | Test(-1); 121 | 122 | return 0; 123 | } 124 | -------------------------------------------------------------------------------- /002_AssignmentOperator.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | class CMyString 8 | { 9 | public: 10 | CMyString(char* pData = NULL); 11 | CMyString(const CMyString& str); 12 | ~CMyString(void); 13 | 14 | CMyString& operator = (const CMyString& str); 15 | 16 | void Print(); 17 | 18 | private: 19 | char* m_pData; 20 | }; 21 | 22 | CMyString::CMyString(char *pData) 23 | { 24 | if(pData == NULL) 25 | { 26 | m_pData = new char[1]; 27 | m_pData[0] = '\0'; 28 | } 29 | else 30 | { 31 | int length = strlen(pData); 32 | m_pData = new char[length + 1]; 33 | strcpy(m_pData, pData); 34 | } 35 | } 36 | 37 | CMyString::CMyString(const CMyString &str) 38 | { 39 | int length = strlen(str.m_pData); 40 | m_pData = new char[length + 1]; 41 | strcpy(m_pData, str.m_pData); 42 | } 43 | 44 | CMyString::~CMyString() 45 | { 46 | delete[] m_pData; 47 | } 48 | 49 | CMyString& CMyString::operator = (const CMyString& str) 50 | { 51 | if(this == &str) 52 | return *this; 53 | 54 | delete []m_pData; 55 | m_pData = NULL; 56 | 57 | m_pData = new char[strlen(str.m_pData) + 1]; 58 | strcpy(m_pData, str.m_pData); 59 | 60 | return *this; 61 | } 62 | 63 | // ==================== Test Code ==================== 64 | 65 | void CMyString::Print() 66 | { 67 | printf("%s", m_pData); 68 | } 69 | 70 | void Test1() 71 | { 72 | printf("Test1 begins:\n"); 73 | 74 | char* text = "Hello world"; 75 | 76 | CMyString str1(text); 77 | CMyString str2; 78 | str2 = str1; 79 | 80 | printf("The expected result is: %s.\n", text); 81 | 82 | printf("The actual result is: "); 83 | str2.Print(); 84 | printf(".\n\n"); 85 | } 86 | 87 | // Assign to self 88 | void Test2() 89 | { 90 | printf("Test2 begins:\n"); 91 | 92 | char* text = "Hello world"; 93 | 94 | CMyString str1(text); 95 | str1 = str1; 96 | 97 | printf("The expected result is: %s.\n", text); 98 | 99 | printf("The actual result is: "); 100 | str1.Print(); 101 | printf(".\n\n"); 102 | } 103 | 104 | // Continuous Assignments 105 | void Test3() 106 | { 107 | printf("Test3 begins:\n"); 108 | 109 | char* text = "Hello world"; 110 | 111 | CMyString str1(text); 112 | CMyString str2, str3; 113 | str3 = str2 = str1; 114 | 115 | printf("The expected result is: %s.\n", text); 116 | 117 | printf("The actual result is: "); 118 | str2.Print(); 119 | printf(".\n"); 120 | 121 | printf("The expected result is: %s.\n", text); 122 | 123 | printf("The actual result is: "); 124 | str3.Print(); 125 | printf(".\n\n"); 126 | } 127 | 128 | int main(int argc, char* argv[]) 129 | { 130 | Test1(); 131 | Test2(); 132 | Test3(); 133 | 134 | return 0; 135 | } 136 | -------------------------------------------------------------------------------- /011_SimpleRegularExpression.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | 6 | bool matchCore(char* string, char* pattern); 7 | 8 | bool match(char* string, char* pattern) 9 | { 10 | if(string == NULL || pattern == NULL) 11 | return false; 12 | 13 | return matchCore(string, pattern); 14 | } 15 | 16 | bool matchCore(char* string, char* pattern) 17 | { 18 | if(*string == '\0' && *pattern == '\0') 19 | return true; 20 | 21 | if(*string != '\0' && *pattern == '\0') 22 | return false; 23 | 24 | if(*(pattern + 1) == '*') 25 | { 26 | if(*pattern == *string || (*pattern == '.' && *string != '\0')) 27 | // move on the next state 28 | return matchCore(string + 1, pattern + 2) 29 | // stay on the current state 30 | || matchCore(string + 1, pattern) 31 | // ignore a '*' 32 | || matchCore(string, pattern + 2); 33 | else 34 | // ignore a '*' 35 | return matchCore(string, pattern + 2); 36 | } 37 | 38 | if(*string == *pattern || (*pattern == '.' && *string != '\0')) 39 | return matchCore(string + 1, pattern + 1); 40 | 41 | return false; 42 | } 43 | 44 | // ==================== Test Code ==================== 45 | 46 | void Test(char* testName, char* string, char* pattern, bool expected) 47 | { 48 | if(testName != NULL) 49 | printf("%s begins: ", testName); 50 | 51 | if(match(string, pattern) == expected) 52 | printf("Passed.\n"); 53 | else 54 | printf("FAILED.\n"); 55 | } 56 | 57 | int main(int argc, char* argv[]) 58 | { 59 | Test("Test01", "", "", true); 60 | Test("Test02", "", ".*", true); 61 | Test("Test03", "", ".", false); 62 | Test("Test04", "", "c*", true); 63 | Test("Test05", "a", ".*", true); 64 | Test("Test06", "a", "a.", false); 65 | Test("Test07", "a", "", false); 66 | Test("Test08", "a", ".", true); 67 | Test("Test09", "a", "ab*", true); 68 | Test("Test10", "a", "ab*a", false); 69 | Test("Test11", "aa", "aa", true); 70 | Test("Test12", "aa", "a*", true); 71 | Test("Test13", "aa", ".*", true); 72 | Test("Test14", "aa", ".", false); 73 | Test("Test15", "ab", ".*", true); 74 | Test("Test16", "ab", ".*", true); 75 | Test("Test17", "aaa", "aa*", true); 76 | Test("Test18", "aaa", "aa.a", false); 77 | Test("Test19", "aaa", "a.a", true); 78 | Test("Test20", "aaa", ".a", false); 79 | Test("Test21", "aaa", "a*a", true); 80 | Test("Test22", "aaa", "ab*a", false); 81 | Test("Test23", "aaa", "ab*ac*a", true); 82 | Test("Test24", "aaa", "ab*a*c*a", true); 83 | Test("Test25", "aaa", ".*", true); 84 | Test("Test26", "aab", "c*a*b", true); 85 | Test("Test27", "aaca", "ab*a*c*a", true); 86 | Test("Test28", "aaba", "ab*a*c*a", false); 87 | Test("Test29", "bbbba", ".*a*a", true); 88 | Test("Test30", "bcbbabab", ".*a*a", false); 89 | 90 | return 0; 91 | } 92 | 93 | -------------------------------------------------------------------------------- /033_CoinChanges.cs: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | using System; 5 | using System.Collections.Generic; 6 | 7 | namespace _033_CoinChanges 8 | { 9 | class Program 10 | { 11 | public static int GetMinCount(int total, int[] coins) 12 | { 13 | int[] counts = new int[total + 1]; 14 | counts[0] = 0; 15 | 16 | const int MAX = Int32.MaxValue; 17 | 18 | for (int i = 1; i <= total; ++i) 19 | { 20 | int count = MAX; 21 | for (int j = 0; j < coins.Length; ++j) 22 | { 23 | if (i - coins[j] >= 0 && count > counts[i - coins[j]]) 24 | count = counts[i - coins[j]]; 25 | } 26 | 27 | if (count < MAX) 28 | counts[i] = count + 1; 29 | else 30 | counts[i] = MAX; 31 | } 32 | 33 | return counts[total]; 34 | } 35 | 36 | // ============================ test code ============================ 37 | private static void Test(String testName, int total, int[] coins, int expected) 38 | { 39 | Console.Write(testName + " begins: "); 40 | 41 | if (GetMinCount(total, coins) == expected) 42 | Console.Write("Passed.\n"); 43 | else 44 | Console.Write("FAILED.\n"); 45 | } 46 | 47 | private static void Test1() 48 | { 49 | int[] coins = { 1, 5, 10, 20, 25 }; 50 | int total = 40; 51 | int expected = 2; 52 | 53 | Test("test1", total, coins, expected); 54 | } 55 | 56 | private static void Test2() 57 | { 58 | int[] coins = { 1, 3, 9, 10 }; 59 | int total = 15; 60 | int expected = 3; 61 | 62 | Test("test2", total, coins, expected); 63 | } 64 | 65 | private static void Test3() 66 | { 67 | int[] coins = { 1, 2, 5, 21, 25 }; 68 | int total = 63; 69 | int expected = 3; 70 | 71 | Test("test3", total, coins, expected); 72 | } 73 | 74 | // Impossible to make changes 75 | private static void Test4() 76 | { 77 | int[] coins = { 2, 4, 8, 16 }; 78 | int total = 63; 79 | int expected = Int32.MaxValue; 80 | 81 | Test("test4", total, coins, expected); 82 | } 83 | 84 | // Total value is in the array for coins 85 | private static void Test5() 86 | { 87 | int[] coins = { 1, 3, 9, 10 }; 88 | int total = 9; 89 | int expected = 1; 90 | 91 | Test("test5", total, coins, expected); 92 | } 93 | 94 | static void Main(string[] args) 95 | { 96 | Test1(); 97 | Test2(); 98 | Test3(); 99 | Test4(); 100 | Test5(); 101 | } 102 | } 103 | } 104 | -------------------------------------------------------------------------------- /088_ThreeNumbersWithSum.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | import java.util.Arrays; 5 | 6 | public class ThreeNumbersWithSum { 7 | public static boolean hasTripleWithSum0(int numbers[]) { 8 | boolean found = false; 9 | if(numbers.length < 3) 10 | return found; 11 | 12 | Arrays.sort(numbers); 13 | 14 | for(int i = 0; i < numbers.length; ++i) { 15 | int sum = -numbers[i]; 16 | found = hasPairWithSum(numbers, sum, i); 17 | 18 | if(found) 19 | break; 20 | } 21 | 22 | return found; 23 | } 24 | 25 | private static boolean hasPairWithSum(int numbers[], int sum, int excludeIndex) { 26 | boolean found = false; 27 | 28 | int ahead = numbers.length - 1; 29 | int behind = 0; 30 | 31 | while(ahead > behind) { 32 | if(ahead == excludeIndex) 33 | ahead--; 34 | if(behind == excludeIndex) 35 | behind++; 36 | 37 | int curSum = numbers[ahead] + numbers[behind]; 38 | 39 | if(curSum == sum) { 40 | found = true; 41 | break; 42 | } 43 | else if(curSum > sum) 44 | ahead --; 45 | else 46 | behind ++; 47 | } 48 | 49 | return found; 50 | } 51 | 52 | //================= Test Code ================= 53 | private static void test(String testName, int numbers[], boolean expected) { 54 | System.out.print(testName + " Begins: "); 55 | 56 | if(hasTripleWithSum0(numbers) == expected) 57 | System.out.println("Passed."); 58 | else 59 | System.out.println("FAILED."); 60 | } 61 | 62 | // The array has three numbers with the sum 0 63 | private static void test1() { 64 | int numbers[] = {1, 2, -4, 7, 11, 3}; 65 | test("test1", numbers, true); 66 | } 67 | 68 | // The array does not have three numbers with the sum 0 69 | private static void test2() { 70 | int numbers[] = {1, 2, 4, 7, 11, 5}; 71 | test("test2", numbers, false); 72 | } 73 | 74 | // The array with three numbers, 75 | // and the sum of three numbers is 0 76 | private static void test3() { 77 | int numbers[] = {1, 2, -3}; 78 | test("test3", numbers, true); 79 | } 80 | 81 | // The array with three numbers, 82 | // and the sum of three numbers is not 0 83 | private static void test4() { 84 | int numbers[] = {1, 2, 3}; 85 | test("test4", numbers, false); 86 | } 87 | 88 | // The length of the array is less than 3, 89 | private static void test5() { 90 | int numbers[] = {1, 2}; 91 | test("test5", numbers, false); 92 | } 93 | 94 | public static void main(String[] args) { 95 | test1(); 96 | test2(); 97 | test3(); 98 | test4(); 99 | test5(); 100 | } 101 | } 102 | -------------------------------------------------------------------------------- /094_QueueWithMax.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | #include 7 | 8 | using namespace std; 9 | 10 | template class QueueWithMax 11 | { 12 | public: 13 | QueueWithMax(): currentIndex(0) 14 | { 15 | } 16 | 17 | void push_back(T number) 18 | { 19 | while(!maximums.empty() && number >= maximums.back().number) 20 | maximums.pop_back(); 21 | 22 | InternalData internalData = {number, currentIndex}; 23 | data.push_back(internalData); 24 | maximums.push_back(internalData); 25 | 26 | ++currentIndex; 27 | } 28 | 29 | void pop_front() 30 | { 31 | if(maximums.empty()) 32 | throw new exception("queue is empty"); 33 | 34 | if(maximums.front().index == data.front().index) 35 | maximums.pop_front(); 36 | 37 | data.pop_front(); 38 | } 39 | 40 | T max() const 41 | { 42 | if(maximums.empty()) 43 | throw new exception("queue is empty"); 44 | 45 | return maximums.front().number; 46 | } 47 | 48 | private: 49 | struct InternalData 50 | { 51 | T number; 52 | int index; 53 | }; 54 | 55 | deque data; 56 | deque maximums; 57 | int currentIndex; 58 | }; 59 | 60 | // ==================== Test Code ==================== 61 | void Test(char* testName, const QueueWithMax& queue, int expected) 62 | { 63 | if(testName != NULL) 64 | printf("%s begins: ", testName); 65 | 66 | if(queue.max() == expected) 67 | printf("Passed.\n"); 68 | else 69 | printf("FAILED.\n"); 70 | } 71 | 72 | int main(int argc, char* argv[]) 73 | { 74 | // 2, 3, 4, 2, 6, 2, 5, 1 75 | 76 | QueueWithMax queue; 77 | // {2} 78 | queue.push_back(2); 79 | Test("Test1", queue, 2); 80 | 81 | // {2, 3} 82 | queue.push_back(3); 83 | Test("Test2", queue, 3); 84 | 85 | // {2, 3, 4} 86 | queue.push_back(4); 87 | Test("Test3", queue, 4); 88 | 89 | // {2, 3, 4, 2} 90 | queue.push_back(2); 91 | Test("Test4", queue, 4); 92 | 93 | // {3, 4, 2} 94 | queue.pop_front(); 95 | Test("Test5", queue, 4); 96 | 97 | // {4, 2} 98 | queue.pop_front(); 99 | Test("Test6", queue, 4); 100 | 101 | // {2} 102 | queue.pop_front(); 103 | Test("Test7", queue, 2); 104 | 105 | // {2, 6} 106 | queue.push_back(6); 107 | Test("Test8", queue, 6); 108 | 109 | // {2, 6, 2} 110 | queue.push_back(2); 111 | Test("Test9", queue, 6); 112 | 113 | // {2, 6, 2, 5} 114 | queue.push_back(5); 115 | Test("Test9", queue, 6); 116 | 117 | // {6, 2, 5} 118 | queue.pop_front(); 119 | Test("Test10", queue, 6); 120 | 121 | // {2, 5} 122 | queue.pop_front(); 123 | Test("Test11", queue, 5); 124 | 125 | // {5} 126 | queue.pop_front(); 127 | Test("Test12", queue, 5); 128 | 129 | // {5, 1} 130 | queue.push_back(1); 131 | Test("Test13", queue, 5); 132 | 133 | return 0; 134 | } 135 | 136 | -------------------------------------------------------------------------------- /007_FindInSortedMatrix.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | 5 | public class FindInMatrix { 6 | 7 | public static boolean find(int matrix[][], int value){ 8 | int rows = matrix.length; 9 | int cols = matrix[0].length; 10 | int start = 0; 11 | int end = rows * cols - 1; 12 | 13 | while (start <= end) { 14 | int mid = start + (end - start) / 2; 15 | int row = mid / cols; 16 | int col = mid % cols; 17 | int v = matrix[row][col]; 18 | 19 | if (v == value) 20 | return true; 21 | 22 | if (v > value) 23 | end = mid - 1; 24 | else 25 | start = mid + 1; 26 | } 27 | 28 | return false; 29 | } 30 | 31 | private static void test(String testName, int matrix[][], int value, boolean expected){ 32 | System.out.print(testName + " begins: "); 33 | 34 | if(find(matrix, value) == expected) 35 | System.out.print("passed.\n"); 36 | else 37 | System.out.print("FAILED.\n"); 38 | } 39 | 40 | // 1 3 5 41 | // 7 9 11 42 | // 13 15 17 43 | // The value to be found, 7, is in the matrix; 44 | private static void test1(){ 45 | int matrix[][] = {{1, 3, 5}, {7, 9, 11}, {13, 15, 17}}; 46 | test("Test1", matrix, 7, true); 47 | } 48 | 49 | // 1 3 5 50 | // 7 9 11 51 | // 13 15 17 52 | // The value to be found, 1, is in the matrix; 53 | private static void test2(){ 54 | int matrix[][] = {{1, 3, 5}, {7, 9, 11}, {13, 15, 17}}; 55 | test("Test2", matrix, 1, true); 56 | } 57 | 58 | // 1 3 5 59 | // 7 9 11 60 | // 13 15 17 61 | // The value to be found, 17, is in the matrix; 62 | private static void test3(){ 63 | int matrix[][] = {{1, 3, 5}, {7, 9, 11}, {13, 15, 17}}; 64 | test("Test3", matrix, 17, true); 65 | } 66 | 67 | // 1 3 5 68 | // 7 9 11 69 | // 13 15 17 70 | // The value to be found, 6, is not in the matrix; 71 | private static void test4(){ 72 | int matrix[][] = {{1, 3, 5}, {7, 9, 11}, {13, 15, 17}}; 73 | test("Test4", matrix, 6, false); 74 | } 75 | 76 | // 1 3 5 77 | // 7 9 11 78 | // 13 15 17 79 | // The value to be found, 0, is not in the matrix; 80 | private static void test5(){ 81 | int matrix[][] = {{1, 3, 5}, {7, 9, 11}, {13, 15, 17}}; 82 | test("Test5", matrix, 0, false); 83 | } 84 | 85 | // 1 3 5 86 | // 7 9 11 87 | // 13 15 17 88 | // The value to be found, 18, is not in the matrix; 89 | private static void test6(){ 90 | int matrix[][] = {{1, 3, 5}, {7, 9, 11}, {13, 15, 17}}; 91 | test("Test6", matrix, 18, false); 92 | } 93 | 94 | public static void main(String[] args) { 95 | test1(); 96 | test2(); 97 | test3(); 98 | test4(); 99 | test5(); 100 | test6(); 101 | } 102 | } 103 | -------------------------------------------------------------------------------- /067_ArrayPermutation.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | import java.util.*; 5 | 6 | public class ArrayPermutation { 7 | static public void permute(ArrayList arrays){ 8 | Stack permutation = new Stack(); 9 | permuteCore(arrays, permutation); 10 | } 11 | 12 | static private void permuteCore(ArrayList arrays, Stack permutation){ 13 | if(permutation.size() == arrays.size()){ 14 | System.out.println(permutation); 15 | return; 16 | } 17 | 18 | int[] array = arrays.get(permutation.size()); 19 | for(int i = 0; i < array.length; ++i){ 20 | permutation.push(array[i]); 21 | permuteCore(arrays, permutation); 22 | permutation.pop(); 23 | } 24 | } 25 | 26 | //================= Test Code ================= 27 | static private void test(String testName, ArrayList arrays){ 28 | System.out.println(testName + " begins: "); 29 | 30 | permute(arrays); 31 | } 32 | 33 | static private void test1(){ 34 | ArrayList arrays = new ArrayList(); 35 | 36 | int[] array1 = {1, 2}; 37 | int[] array2 = {3, 4}; 38 | int[] array3 = {5, 6}; 39 | 40 | arrays.add(array1); 41 | arrays.add(array2); 42 | arrays.add(array3); 43 | 44 | test("Test1", arrays); 45 | } 46 | 47 | static private void test2(){ 48 | ArrayList arrays = new ArrayList(); 49 | 50 | int[] array1 = {1, 2}; 51 | int[] array2 = {3, 4, 5}; 52 | int[] array3 = {6}; 53 | 54 | arrays.add(array1); 55 | arrays.add(array2); 56 | arrays.add(array3); 57 | 58 | test("Test2", arrays); 59 | } 60 | 61 | static private void test3(){ 62 | ArrayList arrays = new ArrayList(); 63 | 64 | int[] array1 = {1, 2, 3}; 65 | int[] array2 = {4, 5, 6}; 66 | int[] array3 = {7, 8}; 67 | 68 | arrays.add(array1); 69 | arrays.add(array2); 70 | arrays.add(array3); 71 | 72 | test("Test3", arrays); 73 | } 74 | 75 | static private void test4(){ 76 | ArrayList arrays = new ArrayList(); 77 | 78 | int[] array1 = {1, 2, 3, 4, 5}; 79 | 80 | arrays.add(array1); 81 | 82 | test("Test4", arrays); 83 | } 84 | 85 | static private void test5(){ 86 | ArrayList arrays = new ArrayList(); 87 | 88 | int[] array1 = {6}; 89 | int[] array2 = {7}; 90 | int[] array3 = {8}; 91 | int[] array4 = {9}; 92 | 93 | arrays.add(array1); 94 | arrays.add(array2); 95 | arrays.add(array3); 96 | arrays.add(array4); 97 | 98 | test("Test4", arrays); 99 | } 100 | 101 | public static void main(String[] args) { 102 | test1(); 103 | test2(); 104 | test3(); 105 | test4(); 106 | test5(); 107 | } 108 | } 109 | -------------------------------------------------------------------------------- /078_DelelteCharacters.c: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | void DeleteCharacters(char* pString, char* pCharsToBeDeleted) 8 | { 9 | int hashTable[256]; 10 | const char* pTemp = pCharsToBeDeleted; 11 | char* pSlow = pString; 12 | char* pFast = pString; 13 | 14 | if(pString == NULL || pCharsToBeDeleted == NULL) 15 | return; 16 | 17 | memset(hashTable, 0, sizeof(hashTable)); 18 | while (*pTemp != '\0') 19 | { 20 | hashTable[*pTemp] = 1; 21 | ++ pTemp; 22 | } 23 | 24 | while (*pFast != '\0') 25 | { 26 | if(hashTable[*pFast] != 1) 27 | { 28 | *pSlow = *pFast; 29 | ++ pSlow; 30 | } 31 | ++pFast; 32 | } 33 | 34 | *pSlow = '\0'; 35 | } 36 | 37 | // ==================== Test Code ==================== 38 | void Test(char* testName, char* pString, char* pCharsToBeDeleted, char* pExpected) 39 | { 40 | if(NULL != testName) 41 | printf("%s begins: ", testName); 42 | 43 | DeleteCharacters(pString, pCharsToBeDeleted); 44 | if((pString == NULL && pExpected == NULL) || (0 == strcmp(pString, pExpected))) 45 | printf("Passed.\n"); 46 | else 47 | printf("FAILED.\n"); 48 | } 49 | 50 | void Test1() 51 | { 52 | char pString[] = "We are students"; 53 | char* pCharsToBeDeleted = "aeiou"; 54 | char* pExpected = "W r stdnts"; 55 | Test("Test1", pString, pCharsToBeDeleted, pExpected); 56 | } 57 | 58 | void Test2() 59 | { 60 | char pString[] = "We are students"; 61 | char* pCharsToBeDeleted = "wxyz"; 62 | char* pExpected = "We are students"; 63 | Test("Test2", pString, pCharsToBeDeleted, pExpected); 64 | } 65 | 66 | void Test3() 67 | { 68 | char pString[] = "8613761352066"; 69 | char* pCharsToBeDeleted = "1234567890"; 70 | char* pExpected = ""; 71 | Test("Test3", pString, pCharsToBeDeleted, pExpected); 72 | } 73 | 74 | void Test4() 75 | { 76 | char pString[] = "119911"; 77 | char* pCharsToBeDeleted = ""; 78 | char* pExpected = "119911"; 79 | Test("Test4", pString, pCharsToBeDeleted, pExpected); 80 | } 81 | 82 | void Test5() 83 | { 84 | char pString[] = "119911"; 85 | char* pCharsToBeDeleted = "aeiou"; 86 | char* pExpected = "119911"; 87 | Test("Test5", pString, pCharsToBeDeleted, pExpected); 88 | } 89 | 90 | void Test6() 91 | { 92 | char pString[] = ""; 93 | char* pCharsToBeDeleted = "aeiou"; 94 | char* pExpected = ""; 95 | Test("Test6", pString, pCharsToBeDeleted, pExpected); 96 | } 97 | 98 | void Test7() 99 | { 100 | char* pString = NULL; 101 | char* pCharsToBeDeleted = "aeiou"; 102 | char* pExpected = NULL; 103 | Test("Test7", pString, pCharsToBeDeleted, pExpected); 104 | } 105 | 106 | void Test8() 107 | { 108 | char pString[] = "abcdefg"; 109 | char* pCharsToBeDeleted = NULL; 110 | char* pExpected = "abcdefg"; 111 | Test("Test8", pString, pCharsToBeDeleted, pExpected); 112 | } 113 | 114 | int main(int argc, char* argv[]) 115 | { 116 | Test1(); 117 | Test2(); 118 | Test3(); 119 | Test4(); 120 | Test5(); 121 | Test6(); 122 | Test7(); 123 | Test8(); 124 | } -------------------------------------------------------------------------------- /056_StackPushPopOrder.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | bool IsPopOrder(const int* pPush, const int* pPop, int nLength) 8 | { 9 | bool bPossible = false; 10 | 11 | if(pPush != NULL && pPop != NULL && nLength > 0) 12 | { 13 | const int* pNextPush = pPush; 14 | const int* pNextPop = pPop; 15 | std::stack stackData; 16 | 17 | while(pNextPop - pPop < nLength) 18 | { 19 | // Push some numbers when the number to be popped is not 20 | // is not on the top of the stack 21 | while(stackData.empty() || stackData.top() != *pNextPop) 22 | { 23 | // Break when all numbers have been pushed 24 | if(pNextPush - pPush == nLength) 25 | break; 26 | 27 | stackData.push(*pNextPush); 28 | pNextPush ++; 29 | } 30 | 31 | if(stackData.top() != *pNextPop) 32 | break; 33 | 34 | stackData.pop(); 35 | pNextPop ++; 36 | } 37 | 38 | if(stackData.empty() && pNextPop - pPop == nLength) 39 | bPossible = true; 40 | } 41 | 42 | return bPossible; 43 | } 44 | 45 | // ==================== Test Code ==================== 46 | void Test(char* testName, const int* pPush, const int* pPop, int nLength, bool expected) 47 | { 48 | if(testName != NULL) 49 | printf("%s begins: ", testName); 50 | 51 | if(IsPopOrder(pPush, pPop, nLength) == expected) 52 | printf("Passed.\n"); 53 | else 54 | printf("failed.\n"); 55 | } 56 | 57 | void Test1() 58 | { 59 | const int nLength = 5; 60 | int push[nLength] = {1, 2, 3, 4, 5}; 61 | int pop[nLength] = {4, 5, 3, 2, 1}; 62 | 63 | Test("Test1", push, pop, nLength, true); 64 | } 65 | 66 | void Test2() 67 | { 68 | const int nLength = 5; 69 | int push[nLength] = {1, 2, 3, 4, 5}; 70 | int pop[nLength] = {3, 5, 4, 2, 1}; 71 | 72 | Test("Test2", push, pop, nLength, true); 73 | } 74 | 75 | void Test3() 76 | { 77 | const int nLength = 5; 78 | int push[nLength] = {1, 2, 3, 4, 5}; 79 | int pop[nLength] = {4, 3, 5, 1, 2}; 80 | 81 | Test("Test3", push, pop, nLength, false); 82 | } 83 | 84 | void Test4() 85 | { 86 | const int nLength = 5; 87 | int push[nLength] = {1, 2, 3, 4, 5}; 88 | int pop[nLength] = {3, 5, 4, 1, 2}; 89 | 90 | Test("Test4", push, pop, nLength, false); 91 | } 92 | 93 | // There is only one element in the push and pop sequences 94 | void Test5() 95 | { 96 | const int nLength = 1; 97 | int push[nLength] = {1}; 98 | int pop[nLength] = {2}; 99 | 100 | Test("Test5", push, pop, nLength, false); 101 | } 102 | 103 | void Test6() 104 | { 105 | const int nLength = 1; 106 | int push[nLength] = {1}; 107 | int pop[nLength] = {1}; 108 | 109 | Test("Test6", push, pop, nLength, true); 110 | } 111 | 112 | void Test7() 113 | { 114 | Test("Test7", NULL, NULL, 0, false); 115 | } 116 | 117 | int main(int argc, char* argv[]) 118 | { 119 | Test1(); 120 | Test2(); 121 | Test3(); 122 | Test4(); 123 | Test5(); 124 | Test6(); 125 | Test7(); 126 | 127 | return 0; 128 | } 129 | -------------------------------------------------------------------------------- /089_SubsetWithSum.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | import java.util.BitSet; 5 | 6 | 7 | public class SubsetWithSum { 8 | public static boolean hasSubsetWithSum0(int numbers[]) { 9 | BitSet bits = new BitSet(numbers.length); 10 | while(increment(bits, numbers.length)) { 11 | int sum = 0; 12 | boolean oneBitAtLeast = false; 13 | for(int i = 0; i < numbers.length; ++i) { 14 | if(bits.get(i)) { 15 | if(!oneBitAtLeast) 16 | oneBitAtLeast = true; 17 | 18 | sum += numbers[i]; 19 | } 20 | } 21 | 22 | if(oneBitAtLeast && sum == 0) 23 | return true; 24 | } 25 | 26 | return false; 27 | } 28 | 29 | private static boolean increment(BitSet bits, int length) { 30 | int index = length - 1; 31 | 32 | while(index >= 0 && bits.get(index)) { 33 | bits.clear(index); 34 | --index; 35 | } 36 | 37 | if(index < 0) 38 | return false; 39 | 40 | bits.set(index); 41 | return true; 42 | } 43 | 44 | // ==================== test code ==================== 45 | private static void test(String testName, int numbers[], boolean expected) { 46 | System.out.print(testName + " Begins: "); 47 | 48 | if(hasSubsetWithSum0(numbers) == expected) 49 | System.out.println("Passed."); 50 | else 51 | System.out.println("FAILED."); 52 | } 53 | // The array has a zero 54 | private static void test1() { 55 | int numbers[] = {1, 2, 4, 0, 11, 15}; 56 | test("test1", numbers, true); 57 | } 58 | 59 | // The array has two numbers whose sum is 0, 60 | private static void test2() { 61 | int numbers[] = {1, 2, -11, 7, 11, 15}; 62 | test("test2", numbers, true); 63 | } 64 | 65 | // The array has three numbers whose sum is 0, 66 | private static void test3() { 67 | int numbers[] = {1, 2, -11, 7, 11, 15}; 68 | test("test3", numbers, true); 69 | } 70 | 71 | // The array has four numbers whose sum is 0, 72 | private static void test4() { 73 | int numbers[] = {1, 2, -11, 7, 8, 15}; 74 | test("test4", numbers, true); 75 | } 76 | 77 | // The array has five numbers whose sum is 0, 78 | private static void test5() { 79 | int numbers[] = {1, 2, -11, 4, 5, 15}; 80 | test("test5", numbers, true); 81 | } 82 | 83 | // The array has six numbers whose sum is 0, 84 | private static void test6() { 85 | int numbers[] = {1, 3, 5, 4, 7, -20}; 86 | test("test6", numbers, true); 87 | } 88 | 89 | // The array does not have a subset with sum is 0, 90 | private static void test7() { 91 | int numbers[] = {1, -3, 5, 4, 7, -20}; 92 | test("test7", numbers, false); 93 | } 94 | 95 | public static void main(String[] args) { 96 | test1(); 97 | test2(); 98 | test3(); 99 | test4(); 100 | test5(); 101 | test6(); 102 | test7(); 103 | } 104 | } 105 | -------------------------------------------------------------------------------- /069_MedianStream.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | using namespace std; 10 | 11 | template class DynamicArray 12 | { 13 | public: 14 | void Insert(T num) 15 | { 16 | if(((minHeap.size() + maxHeap.size()) & 1) == 0) 17 | { 18 | if(maxHeap.size() > 0 && num < maxHeap[0]) 19 | { 20 | maxHeap.push_back(num); 21 | push_heap(maxHeap.begin(), maxHeap.end(), less()); 22 | 23 | num = maxHeap[0]; 24 | 25 | pop_heap(maxHeap.begin(), maxHeap.end(), less()); 26 | maxHeap.pop_back(); 27 | } 28 | 29 | minHeap.push_back(num); 30 | push_heap(minHeap.begin(), minHeap.end(), greater()); 31 | } 32 | else 33 | { 34 | if(minHeap.size() > 0 && minHeap[0] < num) 35 | { 36 | minHeap.push_back(num); 37 | push_heap(minHeap.begin(), minHeap.end(), greater()); 38 | 39 | num = minHeap[0]; 40 | 41 | pop_heap(minHeap.begin(), minHeap.end(), greater()); 42 | minHeap.pop_back(); 43 | } 44 | 45 | maxHeap.push_back(num); 46 | push_heap(maxHeap.begin(), maxHeap.end(), less()); 47 | } 48 | } 49 | 50 | int GetMedian() 51 | { 52 | int size = minHeap.size() + maxHeap.size(); 53 | if(size == 0) 54 | throw exception("No numbers are available"); 55 | 56 | T median = 0; 57 | if(size & 1 == 1) 58 | median = minHeap[0]; 59 | else 60 | median = (minHeap[0] + maxHeap[0]) / 2; 61 | 62 | return median; 63 | } 64 | 65 | private: 66 | vector minHeap; 67 | vector maxHeap; 68 | }; 69 | 70 | // ==================== Test Code ==================== 71 | void Test(char* testName, DynamicArray& numbers, double expected) 72 | { 73 | if(testName != NULL) 74 | printf("%s begins: ", testName); 75 | 76 | if(abs(numbers.GetMedian() - expected) < 0.0000001) 77 | printf("Passed.\n"); 78 | else 79 | printf("FAILED.\n"); 80 | } 81 | 82 | int main(int argc, char* argv[]) 83 | { 84 | DynamicArray numbers; 85 | 86 | printf("Test1 begins: "); 87 | try 88 | { 89 | numbers.GetMedian(); 90 | printf("FAILED.\n"); 91 | } 92 | catch(exception e) 93 | { 94 | printf("Passed.\n"); 95 | } 96 | 97 | numbers.Insert(5); 98 | Test("Test2", numbers, 5); 99 | 100 | numbers.Insert(2); 101 | Test("Test3", numbers, 3.5); 102 | 103 | numbers.Insert(3); 104 | Test("Test4", numbers, 3); 105 | 106 | numbers.Insert(4); 107 | Test("Test6", numbers, 3.5); 108 | 109 | numbers.Insert(1); 110 | Test("Test5", numbers, 3); 111 | 112 | numbers.Insert(6); 113 | Test("Test7", numbers, 3.5); 114 | 115 | numbers.Insert(7); 116 | Test("Test8", numbers, 4); 117 | 118 | numbers.Insert(0); 119 | Test("Test9", numbers, 3.5); 120 | 121 | numbers.Insert(8); 122 | Test("Test10", numbers, 4); 123 | 124 | return 0; 125 | } 126 | 127 | -------------------------------------------------------------------------------- /063_SequenceOfBST.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | 6 | bool VerifySquenceOfBST(int sequence[], int length) 7 | { 8 | if(sequence == NULL || length <= 0) 9 | return false; 10 | 11 | int root = sequence[length - 1]; 12 | 13 | // nodes in left sub-tree are less than root node 14 | int i = 0; 15 | for(; i < length - 1; ++ i) 16 | { 17 | if(sequence[i] > root) 18 | break; 19 | } 20 | 21 | // nodes in right sub-tree are greater than root node 22 | int j = i; 23 | for(; j < length - 1; ++ j) 24 | { 25 | if(sequence[j] < root) 26 | return false; 27 | } 28 | 29 | // Is left sub-tree a binary search tree? 30 | bool left = true; 31 | if(i > 0) 32 | left = VerifySquenceOfBST(sequence, i); 33 | 34 | // Is right sub-tree a binary search tree? 35 | bool right = true; 36 | if(i < length - 1) 37 | right = VerifySquenceOfBST(sequence + i, length - i - 1); 38 | 39 | return (left && right); 40 | } 41 | 42 | // ==================== Test Code ==================== 43 | void Test(char* testName, int sequence[], int length, bool expected) 44 | { 45 | if(testName != NULL) 46 | printf("%s begins: ", testName); 47 | 48 | if(VerifySquenceOfBST(sequence, length) == expected) 49 | printf("passed.\n"); 50 | else 51 | printf("failed.\n"); 52 | } 53 | 54 | // 10 55 | // / \ 56 | // 6 14 57 | // /\ /\ 58 | // 4 8 12 16 59 | void Test1() 60 | { 61 | int data[] = {4, 8, 6, 12, 16, 14, 10}; 62 | Test("Test1", data, sizeof(data)/sizeof(int), true); 63 | } 64 | 65 | // 5 66 | // / \ 67 | // 4 7 68 | // / 69 | // 6 70 | void Test2() 71 | { 72 | int data[] = {4, 6, 7, 5}; 73 | Test("Test2", data, sizeof(data)/sizeof(int), true); 74 | } 75 | 76 | // 5 77 | // / 78 | // 4 79 | // / 80 | // 3 81 | // / 82 | // 2 83 | // / 84 | // 1 85 | void Test3() 86 | { 87 | int data[] = {1, 2, 3, 4, 5}; 88 | Test("Test3", data, sizeof(data)/sizeof(int), true); 89 | } 90 | 91 | // 1 92 | // \ 93 | // 2 94 | // \ 95 | // 3 96 | // \ 97 | // 4 98 | // \ 99 | // 5 100 | void Test4() 101 | { 102 | int data[] = {5, 4, 3, 2, 1}; 103 | Test("Test4", data, sizeof(data)/sizeof(int), true); 104 | } 105 | 106 | // Only one node 107 | void Test5() 108 | { 109 | int data[] = {5}; 110 | Test("Test5", data, sizeof(data)/sizeof(int), true); 111 | } 112 | 113 | void Test6() 114 | { 115 | int data[] = {7, 4, 6, 5}; 116 | Test("Test6", data, sizeof(data)/sizeof(int), false); 117 | } 118 | 119 | void Test7() 120 | { 121 | int data[] = {4, 6, 12, 8, 16, 14, 10}; 122 | Test("Test7", data, sizeof(data)/sizeof(int), false); 123 | } 124 | 125 | // empty 126 | void Test8() 127 | { 128 | Test("Test8", NULL, 0, false); 129 | } 130 | 131 | int main(int argc, char* argv[]) 132 | { 133 | Test1(); 134 | Test2(); 135 | Test3(); 136 | Test4(); 137 | Test5(); 138 | Test6(); 139 | Test7(); 140 | Test8(); 141 | 142 | return 0; 143 | } 144 | 145 | -------------------------------------------------------------------------------- /006_Duplication.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | 5 | public class Duplication { 6 | public static int duplicate(int numbers[]) { 7 | int length = numbers.length; 8 | for(int i = 0; i < length; ++i) { 9 | if(numbers[i] < 0 || numbers[i] > length - 1) 10 | throw new IllegalArgumentException("Invalid numbers."); 11 | } 12 | 13 | for(int i = 0; i < length; ++i) { 14 | while(numbers[i] != i) { 15 | if(numbers[i] == numbers[numbers[i]]) { 16 | return numbers[i]; 17 | } 18 | 19 | // swap numbers[i] and numbers[numbers[i]] 20 | int temp = numbers[i]; 21 | numbers[i] = numbers[temp]; 22 | numbers[temp] = temp; 23 | } 24 | } 25 | 26 | throw new IllegalArgumentException("No duplications."); 27 | } 28 | 29 | //================= Test Code ================= 30 | private static boolean contains(int array[], int number){ 31 | for(int i = 0; i < array.length; ++i){ 32 | if(array[i] == number) 33 | return true; 34 | } 35 | 36 | return false; 37 | } 38 | 39 | private static void test(String testName, int numbers[], int expected[], boolean invalidArgument){ 40 | System.out.print(testName + " begins: "); 41 | 42 | try { 43 | int duplication = duplicate(numbers); 44 | 45 | if(!invalidArgument && contains(expected, duplication)) 46 | System.out.print("Passed.\n"); 47 | else 48 | System.out.print("FAILED.\n"); 49 | } 50 | catch(IllegalArgumentException e){ 51 | if(invalidArgument) 52 | System.out.print("Passed.\n"); 53 | else 54 | System.out.print("FAILED.\n"); 55 | } 56 | } 57 | 58 | // The duplicated number is the smallest number 59 | private static void test1(){ 60 | int numbers[] = {2, 1, 3, 1, 4}; 61 | int duplications[] = {1}; 62 | test("Test1", numbers, duplications, false); 63 | } 64 | 65 | // The duplicated number is the greatest number 66 | private static void test2(){ 67 | int numbers[] = {2, 4, 3, 1, 4}; 68 | int duplications[] = {4}; 69 | test("Test2", numbers, duplications, false); 70 | } 71 | 72 | // There are more than one duplicated number 73 | private static void test3(){ 74 | int numbers[] = {2, 4, 2, 1, 4}; 75 | int duplications[] = {2, 4}; 76 | test("Test3", numbers, duplications, false); 77 | } 78 | 79 | // no duplicated numbers 80 | private static void test4(){ 81 | int numbers[] = {2, 1, 3, 0, 4}; 82 | int duplications[] = {}; 83 | test("Test4", numbers, duplications, true); 84 | } 85 | 86 | // no duplicated numbers 87 | private static void test5(){ 88 | int numbers[] = {2, 1, 3, 5, 4}; 89 | int duplications[] = {}; 90 | test("Test5", numbers, duplications, true); 91 | } 92 | 93 | public static void main(String[] args) { 94 | test1(); 95 | test2(); 96 | test3(); 97 | test4(); 98 | test5(); 99 | } 100 | } 101 | -------------------------------------------------------------------------------- /073_NumberOf1.c: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | #include 7 | 8 | // ==================== Solution 1 ==================== 9 | int NumberOf1(unsigned int n); 10 | 11 | int NumberOf1Between1AndN_Solution1(unsigned int n) 12 | { 13 | int number = 0; 14 | unsigned int i; 15 | 16 | for(i = 0; i <= n; ++ i) 17 | number += NumberOf1(i); 18 | 19 | return number; 20 | } 21 | 22 | int NumberOf1(unsigned int n) 23 | { 24 | int number = 0; 25 | while(n) 26 | { 27 | if(n % 10 == 1) 28 | number ++; 29 | 30 | n = n / 10; 31 | } 32 | 33 | return number; 34 | } 35 | 36 | // ==================== Solution 2 ==================== 37 | int NumberOf1InString(const char* strN); 38 | int PowerBase10(unsigned int n); 39 | 40 | int NumberOf1Between1AndN_Solution2(int n) 41 | { 42 | char strN[50]; 43 | 44 | if(n <= 0) 45 | return 0; 46 | 47 | sprintf(strN, "%d", n); 48 | return NumberOf1InString(strN); 49 | } 50 | 51 | int NumberOf1InString(const char* strN) 52 | { 53 | int first, length; 54 | int numOtherDigits, numRecursive, numFirstDigit; 55 | 56 | if(!strN || *strN < '0' || *strN > '9' || *strN == '\0') 57 | return 0; 58 | 59 | first = *strN - '0'; 60 | length = (unsigned int)(strlen(strN)); 61 | 62 | if(length == 1 && first == 0) 63 | return 0; 64 | 65 | if(length == 1 && first > 0) 66 | return 1; 67 | 68 | // If strN is 21345, numFirstDigit is the number of digit 1 69 | // in the most signification digit in numbers from 10000 to 19999 70 | numFirstDigit = 0; 71 | if(first > 1) 72 | numFirstDigit = PowerBase10(length - 1); 73 | else if(first == 1) 74 | numFirstDigit = atoi(strN + 1) + 1; 75 | 76 | // numOtherDigits is the number of digit 1 in digits except 77 | // the most significant digit in numbers from 01346 to 21345 78 | numOtherDigits = first * (length - 1) * PowerBase10(length - 2); 79 | // numRecursive is the number of digit 1 in numbers from 1 to 1345 80 | numRecursive = NumberOf1InString(strN + 1); 81 | 82 | return numFirstDigit + numOtherDigits + numRecursive; 83 | } 84 | 85 | int PowerBase10(unsigned int n) 86 | { 87 | int i, result = 1; 88 | for(i = 0; i < n; ++ i) 89 | result *= 10; 90 | 91 | return result; 92 | } 93 | 94 | // ==================== Test Code ==================== 95 | void Test(char* testName, int n, int expected) 96 | { 97 | if(testName != NULL) 98 | printf("%s begins: \n", testName); 99 | 100 | if(NumberOf1Between1AndN_Solution1(n) == expected) 101 | printf("Solution1 passed.\n"); 102 | else 103 | printf("Solution1 failed.\n"); 104 | 105 | if(NumberOf1Between1AndN_Solution2(n) == expected) 106 | printf("Solution2 passed.\n"); 107 | else 108 | printf("Solution2 failed.\n"); 109 | 110 | printf("\n"); 111 | } 112 | 113 | int main(int argc, char* argv[]) 114 | { 115 | Test("Test1", 1, 1); 116 | Test("Test2", 5, 1); 117 | Test("Test3", 10, 2); 118 | Test("Test4", 55, 16); 119 | Test("Test5", 99, 20); 120 | Test("Test6", 10000, 4001); 121 | Test("Test7", 21345, 18821); 122 | Test("Test8", 0, 0); 123 | 124 | return 0; 125 | } 126 | 127 | -------------------------------------------------------------------------------- /032_EditDistance.cs: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | using System; 5 | using System.Collections.Generic; 6 | 7 | namespace _032_EditDistance 8 | { 9 | class Program 10 | { 11 | static int GetEditDistance(String str1, String str2) 12 | { 13 | int len1 = str1.Length; ; 14 | int len2 = str2.Length; 15 | 16 | int[,] distances = new int[len2 + 1, len1 + 1]; 17 | 18 | int editDistance = GetEditDistance(str1, str2, distances, len1, len2); 19 | 20 | return editDistance; 21 | } 22 | 23 | static int GetEditDistance(String str1, String str2, int[,] distances, int len1, int len2) 24 | { 25 | for (int i = 0; i < len2 + 1; ++i) 26 | distances[i, 0] = i; 27 | for (int j = 0; j < len1 + 1; ++j) 28 | distances[0, j] = j; 29 | 30 | for (int i = 1; i < len2 + 1; ++i) 31 | { 32 | for (int j = 1; j < len1 + 1; ++j) 33 | { 34 | if (str1[j - 1] == str2[i - 1]) 35 | distances[i, j] = distances[i - 1, j - 1]; 36 | else 37 | { 38 | int deletion = distances[i, j - 1] + 1; 39 | int insertion = distances[i - 1, j] + 1; 40 | int substitution = distances[i - 1, j - 1] + 1; 41 | distances[i, j] = Min(deletion, insertion, substitution); 42 | } 43 | } 44 | } 45 | 46 | return distances[len2, len1]; 47 | } 48 | 49 | static int Min(int num1, int num2, int num3) 50 | { 51 | int less = (num1 < num2) ? num1 : num2; 52 | return (less < num3) ? less : num3; 53 | } 54 | 55 | // ================================ test code ================================ 56 | static void Test(String testName, String str1, String str2, int expected) 57 | { 58 | Console.Write(testName + " begins: "); 59 | 60 | if (GetEditDistance(str1, str2) == expected) 61 | Console.Write("Passed.\n"); 62 | else 63 | Console.Write("FAILED.\n"); 64 | } 65 | 66 | static void Test1() 67 | { 68 | Test("Test1", "kitten", "kitten", 0); 69 | } 70 | 71 | static void Test2() 72 | { 73 | Test("Test2", "kitten", "sitting", 3); 74 | } 75 | 76 | static void Test3() 77 | { 78 | Test("Test3", "Saturday", "Sunday", 3); 79 | } 80 | 81 | static void Test4() 82 | { 83 | Test("Test4", "ant", "parent", 3); 84 | } 85 | 86 | static void Test5() 87 | { 88 | Test("Test5", "parent", "ant", 3); 89 | } 90 | 91 | static void Test6() 92 | { 93 | Test("Test6", "parent", "", 6); 94 | } 95 | 96 | static void Test7() 97 | { 98 | Test("Test7", "", "parent", 6); 99 | } 100 | 101 | static void Main(string[] args) 102 | { 103 | Test1(); 104 | Test2(); 105 | Test3(); 106 | Test4(); 107 | Test5(); 108 | Test6(); 109 | Test7(); 110 | } 111 | } 112 | } 113 | -------------------------------------------------------------------------------- /010_MergeSortedArrays.c: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | 6 | // Supposing there is enough memory at the end of array1, 7 | // in order to accommodate numbers in array2 8 | void merge(int* array1, int length1, int* array2, int length2) 9 | { 10 | int index1, index2, indexMerged; 11 | 12 | if(array1 == NULL || array2 == NULL) 13 | return; 14 | 15 | index1 = length1 - 1; 16 | index2 = length2 - 1; 17 | indexMerged = length1 + length2 - 1; 18 | 19 | while(index1 >= 0 && index2 >= 0) 20 | { 21 | if(array1[index1] >= array2[index2]) 22 | array1[indexMerged--] = array1[index1--]; 23 | else 24 | array1[indexMerged--] = array2[index2--]; 25 | } 26 | 27 | while(index2 >= 0) 28 | array1[indexMerged--] = array2[index2--]; 29 | } 30 | 31 | // ==================== Test Code ==================== 32 | 33 | void Test(char* testName, int* array1, int length1, int* array2, int length2, int* expected) 34 | { 35 | int i; 36 | 37 | if(testName != NULL) 38 | printf("%s begins: ", testName); 39 | 40 | merge(array1, length1, array2, length2); 41 | 42 | if(expected != NULL && array1 != NULL && array2 != NULL) 43 | { 44 | for(i = 0; i < length1 + length2; ++i) 45 | { 46 | if(array1[i] != expected[i]) 47 | break; 48 | } 49 | } 50 | 51 | if((expected == NULL && (array1 == NULL || array2 == NULL)) || (i == length1 + length2)) 52 | printf("passed.\n"); 53 | else 54 | printf("FAILED.\n"); 55 | } 56 | 57 | // no duplicated numbers 58 | void Test1() 59 | { 60 | int array1[20] = {1, 3, 5, 7, 9}; 61 | int array2[] = {2, 4, 6, 8, 10}; 62 | 63 | int expected[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10}; 64 | 65 | Test("Test1", array1, 5, array2, 5, expected); 66 | } 67 | 68 | // no duplicated numbers 69 | void Test2() 70 | { 71 | int array1[20] = {2, 4, 6, 8, 10}; 72 | int array2[] = {1, 3, 5, 7, 9}; 73 | 74 | int expected[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10}; 75 | 76 | Test("Test2", array1, 5, array2, 5, expected); 77 | } 78 | 79 | // duplicated arrays 80 | void Test3() 81 | { 82 | int array1[20] = {2, 4, 6, 8, 10}; 83 | int array2[] = {2, 4, 6, 8, 10}; 84 | 85 | int expected[] = {2, 2, 4, 4, 6, 6, 8, 8, 10, 10}; 86 | 87 | Test("Test3", array1, 5, array2, 5, expected); 88 | } 89 | 90 | // numbers in array1 are less than numbers in array2 91 | void Test4() 92 | { 93 | int array1[20] = {1, 2, 3, 4, 5}; 94 | int array2[] = {6, 7, 8, 9, 10}; 95 | 96 | int expected[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10}; 97 | 98 | Test("Test4", array1, 5, array2, 5, expected); 99 | } 100 | 101 | // numbers in array1 are greater than numbers in array2 102 | void Test5() 103 | { 104 | int array1[20] = {6, 7, 8, 9, 10}; 105 | int array2[] = {1, 2, 3, 4, 5}; 106 | 107 | int expected[] = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10}; 108 | 109 | Test("Test5", array1, 5, array2, 5, expected); 110 | } 111 | 112 | // numbers in array1 are greater than numbers in array2 113 | void Test6() 114 | { 115 | Test("Test6", NULL, 0, NULL, 0, NULL); 116 | } 117 | 118 | int main(int argc, char* argv[]) 119 | { 120 | Test1(); 121 | Test2(); 122 | Test3(); 123 | Test4(); 124 | Test5(); 125 | Test6(); 126 | } 127 | -------------------------------------------------------------------------------- /038_NumbersOccuringOnce.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | 5 | public class NumbersOccuringOnce { 6 | public class NumbersOccurringOnce { 7 | public int num1; 8 | public int num2; 9 | } 10 | 11 | public static void getOnce(int numbers[], NumbersOccurringOnce once){ 12 | if (numbers.length < 2) 13 | return; 14 | 15 | int resultExclusiveOR = 0; 16 | for (int i = 0; i < numbers.length; ++ i) 17 | resultExclusiveOR ^= numbers[i]; 18 | 19 | int indexOf1 = findFirstBitIs1(resultExclusiveOR); 20 | 21 | once.num1 = once.num2 = 0; 22 | for (int j = 0; j < numbers.length; ++ j) { 23 | if(isBit1(numbers[j], indexOf1)) 24 | once.num1 ^= numbers[j]; 25 | else 26 | once.num2 ^= numbers[j]; 27 | } 28 | } 29 | 30 | // The first 1 bit from the rightmost 31 | private static int findFirstBitIs1(int num){ 32 | int indexBit = 0; 33 | while (((num & 1) == 0) && (indexBit < 32)) { 34 | num = num >> 1; 35 | ++ indexBit; 36 | } 37 | 38 | return indexBit; 39 | } 40 | 41 | // check whether the bit with index indexBit is 1 42 | private static boolean isBit1(int num, int indexBit) { 43 | num = num >> indexBit; 44 | return (num & 1) == 1; 45 | } 46 | 47 | //================= Test Code ================= 48 | private static void test(String testName, int[] numbers, NumbersOccurringOnce expected) { 49 | System.out.print(testName + " begins: "); 50 | 51 | NumbersOccuringOnce numbersOnce = new NumbersOccuringOnce(); 52 | NumbersOccurringOnce once = numbersOnce.new NumbersOccurringOnce(); 53 | once.num1 = Integer.MIN_VALUE; 54 | once.num2 = Integer.MAX_VALUE; 55 | 56 | getOnce(numbers, once); 57 | 58 | if((once.num1 == expected.num1 && once.num2 == expected.num2) 59 | || (once.num1 == expected.num2 && once.num2 == expected.num1)) 60 | System.out.print("passed.\n"); 61 | else 62 | System.out.print("FAILED.\n"); 63 | } 64 | 65 | private static void test1() { 66 | int numbers[] = {2, 4, 3, 6, 3, 2, 5, 5}; 67 | NumbersOccuringOnce numbersOnce = new NumbersOccuringOnce(); 68 | NumbersOccurringOnce expected = numbersOnce.new NumbersOccurringOnce(); 69 | expected.num1 = 4; 70 | expected.num2 = 6; 71 | 72 | test("test1", numbers, expected); 73 | } 74 | 75 | private static void test2() { 76 | int numbers[] = {4, 6}; 77 | NumbersOccuringOnce numbersOnce = new NumbersOccuringOnce(); 78 | NumbersOccurringOnce expected = numbersOnce.new NumbersOccurringOnce(); 79 | expected.num1 = 4; 80 | expected.num2 = 6; 81 | 82 | test("test2", numbers, expected); 83 | } 84 | 85 | private static void test3() { 86 | int numbers[] = {4, 6, 1, 1, 1, 1}; 87 | NumbersOccuringOnce numbersOnce = new NumbersOccuringOnce(); 88 | NumbersOccurringOnce expected = numbersOnce.new NumbersOccurringOnce(); 89 | expected.num1 = 4; 90 | expected.num2 = 6; 91 | 92 | test("test3", numbers, expected); 93 | } 94 | 95 | public static void main(String args[]) { 96 | test1(); 97 | test2(); 98 | test3(); 99 | } 100 | } 101 | -------------------------------------------------------------------------------- /098_MaximalProfitBuyingSellingStock.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | 6 | // ==================== Solution 1 ==================== 7 | int MaxDiffCore(int* start, int* end, int* max, int* min); 8 | 9 | int MaxDiff_Solution1(int numbers[], unsigned length) 10 | { 11 | if(numbers == NULL && length < 2) 12 | return 0; 13 | 14 | int max, min; 15 | return MaxDiffCore(numbers, numbers + length - 1, &max, &min); 16 | } 17 | 18 | int MaxDiffCore(int* start, int* end, int* max, int* min) 19 | { 20 | if(end == start) 21 | { 22 | *max = *min = *start; 23 | return 0x80000000; 24 | } 25 | 26 | int* middle = start + (end - start) / 2; 27 | 28 | int maxLeft, minLeft; 29 | int leftDiff = MaxDiffCore(start, middle, &maxLeft, &minLeft); 30 | 31 | int maxRight, minRight; 32 | int rightDiff = MaxDiffCore(middle + 1, end, &maxRight, &minRight); 33 | 34 | int crossDiff = maxRight - minLeft; 35 | 36 | *max = (maxLeft > maxRight) ? maxLeft : maxRight; 37 | *min = (minLeft < minRight) ? minLeft : minRight; 38 | 39 | int maxDiff = (leftDiff > rightDiff) ? leftDiff : rightDiff; 40 | maxDiff = (maxDiff > crossDiff) ? maxDiff : crossDiff; 41 | return maxDiff; 42 | } 43 | 44 | // ==================== Solution 2 ==================== 45 | int MaxDiff_Solution2(int numbers[], unsigned length) 46 | { 47 | if(numbers == NULL && length < 2) 48 | return 0; 49 | 50 | int min = numbers[0]; 51 | int maxDiff = numbers[1] - min; 52 | 53 | for(int i = 2; i < length; ++i) 54 | { 55 | if(numbers[i - 1] < min) 56 | min = numbers[i - 1]; 57 | 58 | int currentDiff = numbers[i] - min; 59 | if(currentDiff > maxDiff) 60 | maxDiff = currentDiff; 61 | } 62 | 63 | return maxDiff; 64 | } 65 | 66 | // ==================== Test Code ==================== 67 | void Test(char* testName, int* numbers, unsigned int length, int expected) 68 | { 69 | if(testName != NULL) 70 | printf("====%s begins: ==== \n", testName); 71 | 72 | if(MaxDiff_Solution1(numbers, length) == expected) 73 | printf("Solution 1 Passed.\n"); 74 | else 75 | printf("Solution 1 FAILED.\n"); 76 | 77 | if(MaxDiff_Solution2(numbers, length) == expected) 78 | printf("Solution 2 Passed.\n"); 79 | else 80 | printf("Solution 2 FAILED.\n"); 81 | } 82 | 83 | void Test1() 84 | { 85 | int numbers[] = {4, 1, 3, 2, 5}; 86 | Test("Test1", numbers, sizeof(numbers) / sizeof(int), 4); 87 | } 88 | 89 | void Test2() 90 | { 91 | int numbers[] = {1, 2, 4, 7, 11, 16}; 92 | Test("Test2", numbers, sizeof(numbers) / sizeof(int), 15); 93 | } 94 | 95 | void Test3() 96 | { 97 | int numbers[] = {16, 11, 7, 4, 2, 1}; 98 | Test("Test3", numbers, sizeof(numbers) / sizeof(int), -1); 99 | } 100 | 101 | void Test4() 102 | { 103 | int numbers[] = {9, 11, 5, 7, 16, 1, 4, 2}; 104 | Test("Test4", numbers, sizeof(numbers) / sizeof(int), 11); 105 | } 106 | 107 | void Test5() 108 | { 109 | int numbers[] = {2, 4}; 110 | Test("Test5", numbers, sizeof(numbers) / sizeof(int), 2); 111 | } 112 | 113 | void Test6() 114 | { 115 | int numbers[] = {4, 2}; 116 | Test("Test6", numbers, sizeof(numbers) / sizeof(int), -2); 117 | } 118 | 119 | int main(int argc, char* argv[]) 120 | { 121 | Test1(); 122 | Test2(); 123 | Test3(); 124 | Test4(); 125 | Test5(); 126 | Test6(); 127 | 128 | return 0; 129 | } 130 | 131 | -------------------------------------------------------------------------------- /003_Singleton.cs: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | using System; 5 | using System.Collections.Generic; 6 | using System.Linq; 7 | using System.Text; 8 | 9 | namespace _003_Singleton 10 | { 11 | public sealed class Singleton1 12 | { 13 | private Singleton1() 14 | { 15 | } 16 | 17 | private static Singleton1 instance = null; 18 | public static Singleton1 Instance 19 | { 20 | get 21 | { 22 | if (instance == null) 23 | instance = new Singleton1(); 24 | 25 | return instance; 26 | } 27 | } 28 | } 29 | 30 | public sealed class Singleton2 31 | { 32 | private Singleton2() 33 | { 34 | } 35 | 36 | private static readonly object syncObj = new object(); 37 | 38 | private static Singleton2 instance = null; 39 | public static Singleton2 Instance 40 | { 41 | get 42 | { 43 | lock (syncObj) 44 | { 45 | if (instance == null) 46 | instance = new Singleton2(); 47 | } 48 | 49 | return instance; 50 | } 51 | } 52 | } 53 | 54 | public sealed class Singleton3 55 | { 56 | private Singleton3() 57 | { 58 | } 59 | 60 | private static object syncObj = new object(); 61 | 62 | private static Singleton3 instance = null; 63 | public static Singleton3 Instance 64 | { 65 | get 66 | { 67 | if (instance == null) 68 | { 69 | lock (syncObj) 70 | { 71 | if (instance == null) 72 | instance = new Singleton3(); 73 | } 74 | } 75 | 76 | return instance; 77 | } 78 | } 79 | } 80 | 81 | public sealed class Singleton4 82 | { 83 | private Singleton4() 84 | { 85 | Console.WriteLine("An instance of Singleton4 is created"); 86 | } 87 | 88 | public static void Print() 89 | { 90 | Console.WriteLine("Singleton4 Print"); 91 | } 92 | 93 | private static Singleton4 instance = new Singleton4(); 94 | public static Singleton4 Instance 95 | { 96 | get 97 | { 98 | return instance; 99 | } 100 | } 101 | } 102 | 103 | public sealed class Singleton5 104 | { 105 | Singleton5() 106 | { 107 | Console.WriteLine("An instance of Singleton5 is created"); 108 | } 109 | 110 | public static void Print() 111 | { 112 | Console.WriteLine("Singleton5 Print"); 113 | } 114 | 115 | public static Singleton5 Instance 116 | { 117 | get 118 | { 119 | return Nested.instance; 120 | } 121 | } 122 | 123 | class Nested 124 | { 125 | static Nested() 126 | { 127 | } 128 | 129 | internal static readonly Singleton5 instance = new Singleton5(); 130 | } 131 | } 132 | 133 | class Program 134 | { 135 | static void Main(string[] args) 136 | { 137 | Singleton4.Print(); 138 | Singleton5.Print(); 139 | } 140 | } 141 | } 142 | -------------------------------------------------------------------------------- /075_UglyNumbers.cs: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | using System; 5 | using System.Collections.Generic; 6 | using System.Linq; 7 | using System.Text; 8 | 9 | namespace _075_UglyNumbers 10 | { 11 | class Program 12 | { 13 | // ================== Solution 1 ================== 14 | private static bool IsUgly(int number) 15 | { 16 | while (number % 2 == 0) 17 | number /= 2; 18 | while (number % 3 == 0) 19 | number /= 3; 20 | while (number % 5 == 0) 21 | number /= 5; 22 | 23 | return (number == 1) ? true : false; 24 | } 25 | 26 | public static int GetUglyNumber_Solution1(int index) 27 | { 28 | if (index <= 0) 29 | return 0; 30 | 31 | int number = 0; 32 | int uglyFound = 0; 33 | while (uglyFound < index) 34 | { 35 | ++number; 36 | 37 | if (IsUgly(number)) 38 | { 39 | ++uglyFound; 40 | } 41 | } 42 | 43 | return number; 44 | } 45 | 46 | // ================== Solution 2 ================== 47 | public static int GetUglyNumber_Solution2(int index) 48 | { 49 | if (index <= 0) 50 | return 0; 51 | 52 | int[] uglyNums = new int[index]; 53 | uglyNums[0] = 1; 54 | int nextUglyIndex = 1; 55 | 56 | int index2 = 0; 57 | int index3 = 0; 58 | int index5 = 0; 59 | 60 | while (nextUglyIndex < index) 61 | { 62 | int min = Math.Min(uglyNums[index2] * 2, uglyNums[index3] * 3); 63 | min = Math.Min(min, uglyNums[index5] * 5); 64 | 65 | uglyNums[nextUglyIndex] = min; 66 | 67 | while (uglyNums[index2] * 2 <= uglyNums[nextUglyIndex]) 68 | ++index2; 69 | while (uglyNums[index3] * 3 <= uglyNums[nextUglyIndex]) 70 | ++index3; 71 | while (uglyNums[index5] * 5 <= uglyNums[nextUglyIndex]) 72 | ++index5; 73 | 74 | ++nextUglyIndex; 75 | } 76 | 77 | int ugly = uglyNums[nextUglyIndex - 1]; 78 | return ugly; 79 | } 80 | 81 | // ==================== Test Code ==================== 82 | static void Test(int index, int expected) 83 | { 84 | Console.WriteLine("Test for index " + index.ToString() + " begins: "); 85 | 86 | if (GetUglyNumber_Solution1(index) == expected) 87 | Console.Write("solution1 passed; "); 88 | else 89 | Console.Write("solution1 FAILD; "); 90 | 91 | if (GetUglyNumber_Solution2(index) == expected) 92 | Console.WriteLine("solution2 passed."); 93 | else 94 | Console.WriteLine("solution2 FAILED."); 95 | } 96 | 97 | 98 | static void Main(string[] args) 99 | { 100 | Test(1, 1); 101 | 102 | Test(2, 2); 103 | Test(3, 3); 104 | Test(4, 4); 105 | Test(5, 5); 106 | Test(6, 6); 107 | Test(7, 8); 108 | Test(8, 9); 109 | Test(9, 10); 110 | Test(10, 12); 111 | Test(11, 15); 112 | 113 | Test(1500, 859963392); 114 | 115 | Test(0, 0); 116 | } 117 | } 118 | } 119 | -------------------------------------------------------------------------------- /085_TreeDepth.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include "..\Utility\BinaryTree.h" 6 | 7 | int TreeDepth(BinaryTreeNode* pRoot) 8 | { 9 | if(pRoot == NULL) 10 | return 0; 11 | 12 | int nLeft = TreeDepth(pRoot->m_pLeft); 13 | int nRight = TreeDepth(pRoot->m_pRight); 14 | 15 | return (nLeft > nRight) ? (nLeft + 1) : (nRight + 1); 16 | } 17 | 18 | // ==================== Test Code ==================== 19 | void Test(char* testName, BinaryTreeNode* pRoot, int expected) 20 | { 21 | if(testName != NULL) 22 | printf("%s begins: ", testName); 23 | 24 | int result = TreeDepth(pRoot); 25 | if(expected == result) 26 | printf("Test passed.\n"); 27 | else 28 | printf("Test failed.\n"); 29 | } 30 | 31 | // 1 32 | // / \ 33 | // 2 3 34 | // /\ \ 35 | // 4 5 6 36 | // / 37 | // 7 38 | void Test1() 39 | { 40 | BinaryTreeNode* pNode1 = CreateBinaryTreeNode(1); 41 | BinaryTreeNode* pNode2 = CreateBinaryTreeNode(2); 42 | BinaryTreeNode* pNode3 = CreateBinaryTreeNode(3); 43 | BinaryTreeNode* pNode4 = CreateBinaryTreeNode(4); 44 | BinaryTreeNode* pNode5 = CreateBinaryTreeNode(5); 45 | BinaryTreeNode* pNode6 = CreateBinaryTreeNode(6); 46 | BinaryTreeNode* pNode7 = CreateBinaryTreeNode(7); 47 | 48 | ConnectTreeNodes(pNode1, pNode2, pNode3); 49 | ConnectTreeNodes(pNode2, pNode4, pNode5); 50 | ConnectTreeNodes(pNode3, NULL, pNode6); 51 | ConnectTreeNodes(pNode5, pNode7, NULL); 52 | 53 | Test("Test1", pNode1, 4); 54 | 55 | DestroyTree(pNode1); 56 | } 57 | 58 | // 1 59 | // / 60 | // 2 61 | // / 62 | // 3 63 | // / 64 | // 4 65 | // / 66 | // 5 67 | void Test2() 68 | { 69 | BinaryTreeNode* pNode1 = CreateBinaryTreeNode(1); 70 | BinaryTreeNode* pNode2 = CreateBinaryTreeNode(2); 71 | BinaryTreeNode* pNode3 = CreateBinaryTreeNode(3); 72 | BinaryTreeNode* pNode4 = CreateBinaryTreeNode(4); 73 | BinaryTreeNode* pNode5 = CreateBinaryTreeNode(5); 74 | 75 | ConnectTreeNodes(pNode1, pNode2, NULL); 76 | ConnectTreeNodes(pNode2, pNode3, NULL); 77 | ConnectTreeNodes(pNode3, pNode4, NULL); 78 | ConnectTreeNodes(pNode4, pNode5, NULL); 79 | 80 | Test("Test2", pNode1, 5); 81 | 82 | DestroyTree(pNode1); 83 | } 84 | 85 | // 1 86 | // \ 87 | // 2 88 | // \ 89 | // 3 90 | // \ 91 | // 4 92 | // \ 93 | // 5 94 | void Test3() 95 | { 96 | BinaryTreeNode* pNode1 = CreateBinaryTreeNode(1); 97 | BinaryTreeNode* pNode2 = CreateBinaryTreeNode(2); 98 | BinaryTreeNode* pNode3 = CreateBinaryTreeNode(3); 99 | BinaryTreeNode* pNode4 = CreateBinaryTreeNode(4); 100 | BinaryTreeNode* pNode5 = CreateBinaryTreeNode(5); 101 | 102 | ConnectTreeNodes(pNode1, NULL, pNode2); 103 | ConnectTreeNodes(pNode2, NULL, pNode3); 104 | ConnectTreeNodes(pNode3, NULL, pNode4); 105 | ConnectTreeNodes(pNode4, NULL, pNode5); 106 | 107 | Test("Test3", pNode1, 5); 108 | 109 | DestroyTree(pNode1); 110 | } 111 | 112 | // Only one node 113 | void Test4() 114 | { 115 | BinaryTreeNode* pNode1 = CreateBinaryTreeNode(1); 116 | Test("Test4", pNode1, 1); 117 | 118 | DestroyTree(pNode1); 119 | } 120 | 121 | // Empty tree 122 | void Test5() 123 | { 124 | Test("Test5", NULL, 0); 125 | } 126 | 127 | int main(int argc, char* argv[]) 128 | { 129 | Test1(); 130 | Test2(); 131 | Test3(); 132 | Test4(); 133 | Test5(); 134 | 135 | return 0; 136 | } 137 | 138 | -------------------------------------------------------------------------------- /023_Fibonacci.c: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | 6 | // ==================== Solution 1 ==================== 7 | long long Fibonacci_Solution1(unsigned int n) 8 | { 9 | if(n <= 0) 10 | return 0; 11 | 12 | if(n == 1) 13 | return 1; 14 | 15 | return Fibonacci_Solution1(n - 1) + Fibonacci_Solution1(n - 2); 16 | } 17 | 18 | // ==================== Solution 2 ==================== 19 | long long Fibonacci_Solution2(unsigned int n) 20 | { 21 | int result[2] = {0, 1}; 22 | long long fibNMinusOne = 1; 23 | long long fibNMinusTwo = 0; 24 | long long fibN = 0; 25 | unsigned int i; 26 | 27 | if(n < 2) 28 | return result[n]; 29 | 30 | for(i = 2; i <= n; ++ i) 31 | { 32 | fibN = fibNMinusOne + fibNMinusTwo; 33 | 34 | fibNMinusTwo = fibNMinusOne; 35 | fibNMinusOne = fibN; 36 | } 37 | 38 | return fibN; 39 | } 40 | 41 | // ==================== Solution 3 ==================== 42 | #include 43 | 44 | struct Matrix2By2 45 | { 46 | long long m_00; 47 | long long m_01; 48 | long long m_10; 49 | long long m_11; 50 | }; 51 | 52 | struct Matrix2By2 MatrixMultiply 53 | ( 54 | const struct Matrix2By2* matrix1, 55 | const struct Matrix2By2* matrix2 56 | ) 57 | { 58 | struct Matrix2By2 result; 59 | result.m_00 = matrix1->m_00 * matrix2->m_00 + matrix1->m_01 * matrix2->m_10; 60 | result.m_01 = matrix1->m_00 * matrix2->m_01 + matrix1->m_01 * matrix2->m_11; 61 | result.m_10 = matrix1->m_10 * matrix2->m_00 + matrix1->m_11 * matrix2->m_10; 62 | result.m_11 = matrix1->m_10 * matrix2->m_01 + matrix1->m_11 * matrix2->m_11; 63 | 64 | return result; 65 | } 66 | 67 | struct Matrix2By2 MatrixPower(unsigned int n) 68 | { 69 | struct Matrix2By2 result; 70 | struct Matrix2By2 unit = {1, 1, 1, 0}; 71 | 72 | assert(n > 0); 73 | if(n == 1) 74 | { 75 | result = unit; 76 | } 77 | else if(n % 2 == 0) 78 | { 79 | result = MatrixPower(n / 2); 80 | result = MatrixMultiply(&result, &result); 81 | } 82 | else if(n % 2 == 1) 83 | { 84 | result = MatrixPower((n - 1) / 2); 85 | result = MatrixMultiply(&result, &result); 86 | result = MatrixMultiply(&result, &unit); 87 | } 88 | 89 | return result; 90 | } 91 | 92 | long long Fibonacci_Solution3(unsigned int n) 93 | { 94 | struct Matrix2By2 PowerNMinus2; 95 | int result[2] = {0, 1}; 96 | 97 | if(n < 2) 98 | return result[n]; 99 | 100 | PowerNMinus2 = MatrixPower(n - 1); 101 | return PowerNMinus2.m_00; 102 | } 103 | 104 | // ==================== Test Code ==================== 105 | void Test(int n, int expected) 106 | { 107 | if(Fibonacci_Solution1(n) == expected) 108 | printf("Test for %d in solution1 passed.\n", n); 109 | else 110 | printf("Test for %d in solution1 failed.\n", n); 111 | 112 | if(Fibonacci_Solution2(n) == expected) 113 | printf("Test for %d in solution2 passed.\n", n); 114 | else 115 | printf("Test for %d in solution2 failed.\n", n); 116 | 117 | if(Fibonacci_Solution3(n) == expected) 118 | printf("Test for %d in solution3 passed.\n", n); 119 | else 120 | printf("Test for %d in solution3 failed.\n", n); 121 | } 122 | 123 | int main(int argc, char* argv[]) 124 | { 125 | Test(0, 0); 126 | Test(1, 1); 127 | Test(2, 1); 128 | Test(3, 2); 129 | Test(4, 3); 130 | Test(5, 5); 131 | Test(6, 8); 132 | Test(7, 13); 133 | Test(8, 21); 134 | Test(9, 34); 135 | Test(10, 55); 136 | 137 | Test(40, 102334155); 138 | 139 | return 0; 140 | } 141 | -------------------------------------------------------------------------------- /043_DeleteNodeInList.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include "..\Utility\List.h" 6 | 7 | void DeleteNode(ListNode** pListHead, ListNode* pToBeDeleted) 8 | { 9 | if(!pListHead || !pToBeDeleted) 10 | return; 11 | 12 | // The node to be deleted is not the tail of the list. 13 | if(pToBeDeleted->m_pNext != NULL) 14 | { 15 | ListNode* pNext = pToBeDeleted->m_pNext; 16 | pToBeDeleted->m_nValue = pNext->m_nValue; 17 | pToBeDeleted->m_pNext = pNext->m_pNext; 18 | 19 | delete pNext; 20 | pNext = NULL; 21 | } 22 | // The list has only one note. Delete the only node. 23 | else if(*pListHead == pToBeDeleted) 24 | { 25 | delete pToBeDeleted; 26 | pToBeDeleted = NULL; 27 | *pListHead = NULL; 28 | } 29 | // Delete the tail node of a list with multiple nodes 30 | else 31 | { 32 | ListNode* pNode = *pListHead; 33 | while(pNode->m_pNext != pToBeDeleted) 34 | { 35 | pNode = pNode->m_pNext; 36 | } 37 | 38 | pNode->m_pNext = NULL; 39 | delete pToBeDeleted; 40 | pToBeDeleted = NULL; 41 | } 42 | } 43 | 44 | // ==================== Test Code ==================== 45 | void Test(ListNode* pListHead, ListNode* pNode) 46 | { 47 | printf("The original list is: \n"); 48 | PrintList(pListHead); 49 | 50 | printf("The node to be deleted is: \n"); 51 | PrintListNode(pNode); 52 | 53 | DeleteNode(&pListHead, pNode); 54 | 55 | printf("The result list is: \n"); 56 | PrintList(pListHead); 57 | printf("\n\n"); 58 | } 59 | 60 | // Delete a node 61 | void Test1() 62 | { 63 | ListNode* pNode1 = CreateListNode(1); 64 | ListNode* pNode2 = CreateListNode(2); 65 | ListNode* pNode3 = CreateListNode(3); 66 | ListNode* pNode4 = CreateListNode(4); 67 | ListNode* pNode5 = CreateListNode(5); 68 | 69 | ConnectListNodes(pNode1, pNode2); 70 | ConnectListNodes(pNode2, pNode3); 71 | ConnectListNodes(pNode3, pNode4); 72 | ConnectListNodes(pNode4, pNode5); 73 | 74 | Test(pNode1, pNode3); 75 | 76 | DestroyList(pNode1); 77 | } 78 | 79 | // Delete a tail 80 | void Test2() 81 | { 82 | ListNode* pNode1 = CreateListNode(1); 83 | ListNode* pNode2 = CreateListNode(2); 84 | ListNode* pNode3 = CreateListNode(3); 85 | ListNode* pNode4 = CreateListNode(4); 86 | ListNode* pNode5 = CreateListNode(5); 87 | 88 | ConnectListNodes(pNode1, pNode2); 89 | ConnectListNodes(pNode2, pNode3); 90 | ConnectListNodes(pNode3, pNode4); 91 | ConnectListNodes(pNode4, pNode5); 92 | 93 | Test(pNode1, pNode5); 94 | 95 | DestroyList(pNode1); 96 | } 97 | 98 | // Delete a header node 99 | void Test3() 100 | { 101 | ListNode* pNode1 = CreateListNode(1); 102 | ListNode* pNode2 = CreateListNode(2); 103 | ListNode* pNode3 = CreateListNode(3); 104 | ListNode* pNode4 = CreateListNode(4); 105 | ListNode* pNode5 = CreateListNode(5); 106 | 107 | ConnectListNodes(pNode1, pNode2); 108 | ConnectListNodes(pNode2, pNode3); 109 | ConnectListNodes(pNode3, pNode4); 110 | ConnectListNodes(pNode4, pNode5); 111 | 112 | Test(pNode1, pNode1); 113 | 114 | DestroyList(pNode1); 115 | } 116 | 117 | // Delete the only node 118 | void Test4() 119 | { 120 | ListNode* pNode1 = CreateListNode(1); 121 | 122 | Test(pNode1, pNode1); 123 | } 124 | 125 | // empty list 126 | void Test5() 127 | { 128 | Test(NULL, NULL); 129 | } 130 | 131 | int main(int argc, char* argv[]) 132 | { 133 | Test1(); 134 | Test2(); 135 | Test3(); 136 | Test4(); 137 | Test5(); 138 | 139 | return 0; 140 | } 141 | -------------------------------------------------------------------------------- /100_103_ArithmeticOperations.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | public class ArithmeticOperations { 5 | 6 | public static int add(int num1, int num2) { 7 | int sum, carry; 8 | do { 9 | sum = num1 ^ num2; 10 | carry = (num1 & num2) << 1; 11 | num1 = sum; 12 | num2 = carry; 13 | } while (num2 != 0); 14 | 15 | return num1; 16 | } 17 | 18 | public static int subtract(int num1, int num2) { 19 | num2 = add(~num2, 1); 20 | return add(num1, num2); 21 | } 22 | 23 | public static int multiply(int num1, int num2) { 24 | boolean minus = false; 25 | if ((num1 < 0 && num2 > 0) || (num1 > 0 && num2 < 0)) 26 | minus = true; 27 | 28 | if (num1 < 0) 29 | num1 = add(~num1, 1); 30 | if (num2 < 0) 31 | num2 = add(~num2, 1); 32 | 33 | int result = 0; 34 | while (num1 > 0) { 35 | if ((num1 & 0x1) != 0) { 36 | result = add(result, num2); 37 | } 38 | 39 | num2 = num2 << 1; 40 | num1 = num1 >> 1; 41 | } 42 | 43 | if (minus) 44 | result = add(~result, 1); 45 | 46 | return result; 47 | } 48 | 49 | public static int divide(int num1, int num2) { 50 | if (num2 == 0) 51 | throw new ArithmeticException("num2 is zero."); 52 | 53 | boolean minus = false; 54 | if ((num1 < 0 && num2 > 0) || (num1 > 0 && num2 < 0)) 55 | minus = true; 56 | 57 | if (num1 < 0) 58 | num1 = add(~num1, 1); 59 | if (num2 < 0) 60 | num2 = add(~num2, 1); 61 | 62 | int result = 0; 63 | for (int i = 0; i < 32; i=add(i, 1)) { 64 | result = result << 1; 65 | if ((num1 >> (31 - i)) >= num2) { 66 | num1 = subtract(num1, num2 << (31 - i)); 67 | result = add(result, 1); 68 | } 69 | } 70 | 71 | if (minus) 72 | result = add(~result, 1); 73 | 74 | return result; 75 | } 76 | 77 | public static void test(String testName, int num1, int num2, int res1, 78 | int res2, int res3, int res4) { 79 | System.out.print(testName + " begins: "); 80 | 81 | if (add(num1, num2) == res1) 82 | System.out.print("add passed, "); 83 | else 84 | System.out.print("add FAILED, "); 85 | 86 | if (subtract(num1, num2) == res2) 87 | System.out.print("subtract passed, "); 88 | else 89 | System.out.print("subtract FAILED, "); 90 | 91 | if (multiply(num1, num2) == res3) 92 | System.out.print("multiply passed, "); 93 | else 94 | System.out.print("multiply FAILED, "); 95 | 96 | try { 97 | int result = divide(num1, num2); 98 | if (num2 != 0 && result == res4) 99 | System.out.print("divide passed."); 100 | else 101 | System.out.print("divide FAILED."); 102 | } catch (ArithmeticException e) { 103 | if (num2 == 0) 104 | System.out.print("divide passed."); 105 | else 106 | System.out.print("divide FAILED."); 107 | } 108 | 109 | System.out.print("\n"); 110 | } 111 | 112 | public static void main(String[] args) { 113 | test("Test1", 3, 2, 5, 1, 6, 1); 114 | test("Test2", -3, 2, -1, -5, -6, -1); 115 | test("Test3", -3, -2, -5, -1, 6, 1); 116 | test("Test4", -3, 0, -3, -3, 0, 0); 117 | test("Test5", 100, -5, 95, 105, -500, -20); 118 | test("Test6", 98, 5, 103, 93, 490, 19); 119 | test("Test7", 6, 12, 18, -6, 72, 0); 120 | } 121 | } 122 | -------------------------------------------------------------------------------- /009_ReplaceBlanks.c: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | /*capacity is total capacity of a string, which is longer than its actual length*/ 8 | void ReplaceBlank(char string[], int capacity) 9 | { 10 | int originalLength, numberOfBlank, newLength; 11 | int i, indexOfOriginal, indexOfNew; 12 | 13 | if(string == NULL || capacity <= 0) 14 | return; 15 | 16 | /*originalLength is the actual length of string*/ 17 | originalLength = numberOfBlank = i = 0; 18 | while(string[i] != '\0') 19 | { 20 | ++ originalLength; 21 | 22 | if(string[i] == ' ') 23 | ++ numberOfBlank; 24 | 25 | ++ i; 26 | } 27 | 28 | /*newLength is the length of the replaced string*/ 29 | newLength = originalLength + numberOfBlank * 2; 30 | if(newLength > capacity) 31 | return; 32 | 33 | indexOfOriginal = originalLength; 34 | indexOfNew = newLength; 35 | while(indexOfOriginal >= 0 && indexOfNew > indexOfOriginal) 36 | { 37 | if(string[indexOfOriginal] == ' ') 38 | { 39 | string[indexOfNew --] = '0'; 40 | string[indexOfNew --] = '2'; 41 | string[indexOfNew --] = '%'; 42 | } 43 | else 44 | { 45 | string[indexOfNew --] = string[indexOfOriginal]; 46 | } 47 | 48 | -- indexOfOriginal; 49 | } 50 | } 51 | 52 | void Test(char* testName, char string[], int length, char expected[]) 53 | { 54 | if(testName != NULL) 55 | printf("%s begins: ", testName); 56 | 57 | ReplaceBlank(string, length); 58 | 59 | if(expected == NULL && string == NULL) 60 | printf("passed.\n"); 61 | else if(expected == NULL && string != NULL) 62 | printf("failed.\n"); 63 | else if(strcmp(string, expected) == 0) 64 | printf("passed.\n"); 65 | else 66 | printf("failed.\n"); 67 | } 68 | 69 | #define LENGTH 100 70 | 71 | // A blank is inside a sentence 72 | void Test1() 73 | { 74 | char string[LENGTH] = "hello world"; 75 | Test("Test1", string, LENGTH, "hello%20world"); 76 | } 77 | 78 | // A blank is at the beginning of a sentence 79 | void Test2() 80 | { 81 | char string[LENGTH] = " helloworld"; 82 | Test("Test2", string, LENGTH, "%20helloworld"); 83 | } 84 | 85 | // A blank is at the end of a sentence 86 | void Test3() 87 | { 88 | char string[LENGTH] = "helloworld "; 89 | Test("Test3", string, LENGTH, "helloworld%20"); 90 | } 91 | 92 | // Two adjcent blanks 93 | void Test4() 94 | { 95 | char string[LENGTH] = "hello world"; 96 | Test("Test4", string, LENGTH, "hello%20%20world"); 97 | } 98 | 99 | // NULL 100 | void Test5() 101 | { 102 | Test("Test5", NULL, 0, NULL); 103 | } 104 | 105 | // Empty string 106 | void Test6() 107 | { 108 | char string[LENGTH] = ""; 109 | Test("Test6", string, LENGTH, ""); 110 | } 111 | 112 | // Input string only has a blank 113 | void Test7() 114 | { 115 | char string[LENGTH] = " "; 116 | Test("Test7", string, LENGTH, "%20"); 117 | } 118 | 119 | // No blanks in the input 120 | void Test8() 121 | { 122 | char string[LENGTH] = "helloworld"; 123 | Test("Test8", string, LENGTH, "helloworld"); 124 | } 125 | 126 | // Input string only has blanks 127 | void Test9() 128 | { 129 | char string[LENGTH] = " "; 130 | Test("Test9", string, LENGTH, "%20%20%20"); 131 | } 132 | 133 | // Multiple blanks among words 134 | void Test10() 135 | { 136 | char string[LENGTH] = "Multiple blanks among words"; 137 | Test("Test10", string, LENGTH, "Multiple%20blanks%20among%20words"); 138 | } 139 | 140 | int main(int argc, char* argv[]) 141 | { 142 | Test1(); 143 | Test2(); 144 | Test3(); 145 | Test4(); 146 | Test5(); 147 | Test6(); 148 | Test7(); 149 | Test8(); 150 | Test9(); 151 | Test10(); 152 | 153 | return 0; 154 | } 155 | -------------------------------------------------------------------------------- /057_PrintTreeByLevel.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include "..\Utility\BinaryTree.h" 6 | #include 7 | 8 | void PrintFromTopToBottom(BinaryTreeNode* pRoot) 9 | { 10 | if(pRoot == NULL) 11 | return; 12 | 13 | std::queue queueTreeNodes; 14 | queueTreeNodes.push(pRoot); 15 | 16 | while(queueTreeNodes.size() > 0) 17 | { 18 | BinaryTreeNode *pNode = queueTreeNodes.front(); 19 | queueTreeNodes.pop(); 20 | 21 | printf("%d ", pNode->m_nValue); 22 | 23 | if(pNode->m_pLeft) 24 | queueTreeNodes.push(pNode->m_pLeft); 25 | 26 | if(pNode->m_pRight) 27 | queueTreeNodes.push(pNode->m_pRight); 28 | } 29 | } 30 | 31 | // ==================== Test Code ==================== 32 | void Test(char* testName, BinaryTreeNode* pRoot) 33 | { 34 | if(testName != NULL) 35 | printf("%s begins: \n", testName); 36 | 37 | PrintTree(pRoot); 38 | 39 | printf("The nodes from top to bottom, from left to right are: \n"); 40 | PrintFromTopToBottom(pRoot); 41 | 42 | printf("\n\n"); 43 | } 44 | 45 | // 10 46 | // / \ 47 | // 6 14 48 | // /\ /\ 49 | // 4 8 12 16 50 | void Test1() 51 | { 52 | BinaryTreeNode* pNode10 = CreateBinaryTreeNode(10); 53 | BinaryTreeNode* pNode6 = CreateBinaryTreeNode(6); 54 | BinaryTreeNode* pNode14 = CreateBinaryTreeNode(14); 55 | BinaryTreeNode* pNode4 = CreateBinaryTreeNode(4); 56 | BinaryTreeNode* pNode8 = CreateBinaryTreeNode(8); 57 | BinaryTreeNode* pNode12 = CreateBinaryTreeNode(12); 58 | BinaryTreeNode* pNode16 = CreateBinaryTreeNode(16); 59 | 60 | ConnectTreeNodes(pNode10, pNode6, pNode14); 61 | ConnectTreeNodes(pNode6, pNode4, pNode8); 62 | ConnectTreeNodes(pNode14, pNode12, pNode16); 63 | 64 | Test("Test1", pNode10); 65 | 66 | DestroyTree(pNode10); 67 | } 68 | 69 | // 5 70 | // / 71 | // 4 72 | // / 73 | // 3 74 | // / 75 | // 2 76 | // / 77 | // 1 78 | void Test2() 79 | { 80 | BinaryTreeNode* pNode5 = CreateBinaryTreeNode(5); 81 | BinaryTreeNode* pNode4 = CreateBinaryTreeNode(4); 82 | BinaryTreeNode* pNode3 = CreateBinaryTreeNode(3); 83 | BinaryTreeNode* pNode2 = CreateBinaryTreeNode(2); 84 | BinaryTreeNode* pNode1 = CreateBinaryTreeNode(1); 85 | 86 | ConnectTreeNodes(pNode5, pNode4, NULL); 87 | ConnectTreeNodes(pNode4, pNode3, NULL); 88 | ConnectTreeNodes(pNode3, pNode2, NULL); 89 | ConnectTreeNodes(pNode2, pNode1, NULL); 90 | 91 | Test("Test2", pNode5); 92 | 93 | DestroyTree(pNode5); 94 | } 95 | 96 | // 1 97 | // \ 98 | // 2 99 | // \ 100 | // 3 101 | // \ 102 | // 4 103 | // \ 104 | // 5 105 | void Test3() 106 | { 107 | BinaryTreeNode* pNode1 = CreateBinaryTreeNode(1); 108 | BinaryTreeNode* pNode2 = CreateBinaryTreeNode(2); 109 | BinaryTreeNode* pNode3 = CreateBinaryTreeNode(3); 110 | BinaryTreeNode* pNode4 = CreateBinaryTreeNode(4); 111 | BinaryTreeNode* pNode5 = CreateBinaryTreeNode(5); 112 | 113 | ConnectTreeNodes(pNode1, NULL, pNode2); 114 | ConnectTreeNodes(pNode2, NULL, pNode3); 115 | ConnectTreeNodes(pNode3, NULL, pNode4); 116 | ConnectTreeNodes(pNode4, NULL, pNode5); 117 | 118 | Test("Test3", pNode1); 119 | 120 | DestroyTree(pNode1); 121 | } 122 | 123 | // There is only one node in a tree 124 | void Test4() 125 | { 126 | BinaryTreeNode* pNode1 = CreateBinaryTreeNode(1); 127 | Test("Test4", pNode1); 128 | 129 | DestroyTree(pNode1); 130 | } 131 | 132 | // empty tree 133 | void Test5() 134 | { 135 | Test("Test5", NULL); 136 | } 137 | 138 | int main(int argc, char* argv[]) 139 | { 140 | Test1(); 141 | Test2(); 142 | Test3(); 143 | Test4(); 144 | Test5(); 145 | 146 | return 0; 147 | } 148 | 149 | -------------------------------------------------------------------------------- /099_Accumulate.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | 6 | // ==================== Solution 1 ==================== 7 | class Temp 8 | { 9 | public: 10 | Temp() { ++ N; Sum += N; } 11 | 12 | static void Reset() { N = 0; Sum = 0; } 13 | static unsigned int GetSum() { return Sum; } 14 | 15 | private: 16 | static unsigned int N; 17 | static unsigned int Sum; 18 | }; 19 | 20 | unsigned int Temp::N = 0; 21 | unsigned int Temp::Sum = 0; 22 | 23 | unsigned int Sum_Solution1(unsigned int n) 24 | { 25 | Temp::Reset(); 26 | 27 | Temp *a = new Temp[n]; 28 | delete []a; 29 | a = NULL; 30 | 31 | return Temp::GetSum(); 32 | } 33 | 34 | // ==================== Solution 2 ==================== 35 | class A; 36 | A* Array[2]; 37 | 38 | class A 39 | { 40 | public: 41 | virtual unsigned int Sum (unsigned int n) 42 | { 43 | return 0; 44 | } 45 | }; 46 | 47 | class B: public A 48 | { 49 | public: 50 | virtual unsigned int Sum (unsigned int n) 51 | { 52 | return Array[!!n]->Sum(n-1) + n; 53 | } 54 | }; 55 | 56 | int Sum_Solution2(int n) 57 | { 58 | A a; 59 | B b; 60 | Array[0] = &a; 61 | Array[1] = &b; 62 | 63 | int value = Array[1]->Sum(n); 64 | 65 | return value; 66 | } 67 | 68 | // ==================== Solution 3 ==================== 69 | typedef unsigned int (*fun)(unsigned int); 70 | 71 | unsigned int Solution3_Teminator(unsigned int n) 72 | { 73 | return 0; 74 | } 75 | 76 | unsigned int Sum_Solution3(unsigned int n) 77 | { 78 | static fun f[2] = {Solution3_Teminator, Sum_Solution3}; 79 | return n + f[!!n](n - 1); 80 | } 81 | 82 | // ==================== Solution 4 ==================== 83 | template struct Sum_Solution4 84 | { 85 | enum Value { N = Sum_Solution4::N + n}; 86 | }; 87 | 88 | template <> struct Sum_Solution4<1> 89 | { 90 | enum Value { N = 1}; 91 | }; 92 | 93 | template <> struct Sum_Solution4<0> 94 | { 95 | enum Value { N = 0}; 96 | }; 97 | 98 | // ==================== Test Code ==================== 99 | void Test(int n, int expected) 100 | { 101 | printf("Test for %d begins:\n", n); 102 | 103 | if(Sum_Solution1(n) == expected) 104 | printf("Solution1 passed.\n"); 105 | else 106 | printf("Solution1 failed.\n"); 107 | 108 | if(Sum_Solution2(n) == expected) 109 | printf("Solution2 passed.\n"); 110 | else 111 | printf("Solution2 failed.\n"); 112 | 113 | if(Sum_Solution3(n) == expected) 114 | printf("Solution3 passed.\n"); 115 | else 116 | printf("Solution3 failed.\n"); 117 | } 118 | 119 | void Test1() 120 | { 121 | const unsigned int number = 1; 122 | int expected = 1; 123 | Test(number, expected); 124 | if(Sum_Solution4::N == expected) 125 | printf("Solution4 passed.\n"); 126 | else 127 | printf("Solution4 failed.\n"); 128 | } 129 | 130 | void Test2() 131 | { 132 | const unsigned int number = 5; 133 | int expected = 15; 134 | Test(number, expected); 135 | if(Sum_Solution4::N == expected) 136 | printf("Solution4 passed.\n"); 137 | else 138 | printf("Solution4 failed.\n"); 139 | } 140 | 141 | void Test3() 142 | { 143 | const unsigned int number = 10; 144 | int expected = 55; 145 | Test(number, expected); 146 | if(Sum_Solution4::N == expected) 147 | printf("Solution4 passed.\n"); 148 | else 149 | printf("Solution4 failed.\n"); 150 | } 151 | 152 | void Test4() 153 | { 154 | const unsigned int number = 0; 155 | int expected = 0; 156 | Test(number, expected); 157 | if(Sum_Solution4::N == expected) 158 | printf("Solution4 passed.\n"); 159 | else 160 | printf("Solution4 failed.\n"); 161 | } 162 | 163 | int main(int argc, char* argv[]) 164 | { 165 | Test1(); 166 | Test2(); 167 | Test3(); 168 | Test4(); 169 | 170 | return 0; 171 | } 172 | -------------------------------------------------------------------------------- /097_MinimalMoves.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | public class MinimalMoves { 5 | // ==================== Solution 1 ==================== 6 | public static int minMoveCount_solution1(int[] seq) { 7 | return seq.length - longestIncreasingLength_solution1(seq); 8 | } 9 | 10 | private static int longestIncreasingLength_solution1(int[] seq){ 11 | int len = seq.length; 12 | int[] lookup = new int[len]; 13 | 14 | for(int i = 0; i < len; ++i) { 15 | int longestSoFar = 0; 16 | for(int j= 0; j < i; ++j) { 17 | if(seq[i] > seq[j] && lookup[j] > longestSoFar) 18 | longestSoFar = lookup[j]; 19 | } 20 | lookup[i] = longestSoFar + 1; 21 | } 22 | 23 | int longestLength = 0; 24 | for(int i = 0; i < len; ++i) { 25 | if(lookup[i] > longestLength) 26 | longestLength = lookup[i]; 27 | } 28 | 29 | return longestLength; 30 | } 31 | 32 | // ==================== Solution 2 ==================== 33 | public static int minMoveCount_solution2(int[] seq) { 34 | return seq.length - longestIncreasingLength_solution2(seq); 35 | } 36 | 37 | private static int longestIncreasingLength_solution2(int[] seq){ 38 | int len = seq.length; 39 | int[] lookup = new int[len]; 40 | 41 | lookup[0] = seq[0]; 42 | int longestLength = 1; 43 | for(int i = 1; i < len; ++i) { 44 | if(seq[i] > lookup[longestLength - 1]) { 45 | longestLength++; 46 | lookup[longestLength - 1] = seq[i]; 47 | } 48 | else { 49 | int low = 0; 50 | int high = longestLength - 1; 51 | while(low != high) { 52 | int mid = (low + high) / 2; 53 | if(lookup[mid] < seq[i]) { 54 | low = mid + 1; 55 | } 56 | else { 57 | high = mid; 58 | } 59 | } 60 | 61 | lookup[low] = seq[i]; 62 | } 63 | } 64 | 65 | return longestLength; 66 | } 67 | 68 | // ==================== Test Code ==================== 69 | private static void test(String testName, int cards[], int expected){ 70 | System.out.print(testName + " begins: "); 71 | if(minMoveCount_solution1(cards) == expected) 72 | System.out.print("Passed; "); 73 | else 74 | System.out.print("FAILED; "); 75 | 76 | if(minMoveCount_solution2(cards) == expected) 77 | System.out.println("Passed."); 78 | else 79 | System.out.println("FAILED."); 80 | } 81 | 82 | private static void test1(){ 83 | int cards[] = {2, 4, 1, 5, 6, 3}; 84 | test("Test1", cards, 2); 85 | } 86 | 87 | private static void test2(){ 88 | int cards[] = {1, 2, 5, 3, 4, 7, 6}; 89 | test("Test2", cards, 2); 90 | } 91 | 92 | private static void test3(){ 93 | int cards[] = {7, 2, 3, 1, 4, 5, 8, 9, 6}; 94 | test("Test3", cards, 3); 95 | } 96 | 97 | private static void test4(){ 98 | int cards[] = {8, 4, 12, 2, 10, 6, 14, 1, 9, 5, 13, 3, 11, 7}; 99 | test("Test4", cards, 10); 100 | } 101 | 102 | private static void test5(){ 103 | int cards[] = {1, 2, 3, 4, 5, 6, 7}; 104 | test("Test5", cards, 0); 105 | } 106 | 107 | private static void test6(){ 108 | int cards[] = {7, 6, 5, 4, 3, 2, 1}; 109 | test("Test6", cards, 6); 110 | } 111 | 112 | private static void test7(){ 113 | int cards[] = {7}; 114 | test("Test7", cards, 0); 115 | } 116 | 117 | public static void main(String[] args) { 118 | test1(); 119 | test2(); 120 | test3(); 121 | test4(); 122 | test5(); 123 | test6(); 124 | test7(); 125 | } 126 | } -------------------------------------------------------------------------------- /042_AddNumericStrings.c: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | 7 | int checkInvalidInput(char* num1, char* num2, char* sum); 8 | void reverse(char* str); 9 | 10 | /* It returns -1 if the input invalid, otherwise returns 0. */ 11 | int add(char* num1, char* num2, char* sum) 12 | { 13 | int index1, index2, indexSum; 14 | int sumDigit, carry, digit1, digit2; 15 | 16 | if(checkInvalidInput(num1, num2, sum)) 17 | return -1; 18 | 19 | reverse(num1); 20 | reverse(num2); 21 | 22 | index1 = index2 = indexSum = 0; 23 | carry = 0; 24 | while(num1[index1] != '\0' || num2[index2] != '\0') 25 | { 26 | digit1 = (num1[index1] == '\0') ? 0 : num1[index1] - '0'; 27 | digit2 = (num2[index2] == '\0') ? 0 : num2[index2] - '0'; 28 | 29 | sumDigit = digit1 + digit2 + carry; 30 | carry = (sumDigit >= 10) ? 1 : 0; 31 | sumDigit = (sumDigit >= 10) ? sumDigit - 10 : sumDigit; 32 | 33 | sum[indexSum++] = sumDigit + '0'; 34 | 35 | if(num1[index1] != '\0') 36 | ++index1; 37 | if(num2[index2] != '\0') 38 | ++index2; 39 | } 40 | 41 | if(carry != 0) 42 | sum[indexSum++] = carry + '0'; 43 | 44 | sum[indexSum] = '\0'; 45 | reverse(sum); 46 | 47 | return 0; 48 | } 49 | 50 | int checkInvalidInput(char* num1, char* num2, char* sum) 51 | { 52 | int length1, length2, i; 53 | 54 | if(num1 == NULL || num2 == NULL || sum == NULL) 55 | return -1; 56 | 57 | length1 = strlen(num1); 58 | for(i = 0; i < length1; ++i) 59 | { 60 | if(num1[i] < '0' || num1[i] > '9') 61 | return -1; 62 | } 63 | 64 | length2 = strlen(num2); 65 | for(i = 0; i < length2; ++i) 66 | { 67 | if(num2[i] < '0' || num2[i] > '9') 68 | return -1; 69 | } 70 | 71 | return 0; 72 | } 73 | 74 | void reverse(char* str) 75 | { 76 | int i, length; 77 | char temp; 78 | 79 | length = strlen(str); 80 | for(i = 0; i < length / 2; ++i) 81 | { 82 | temp = str[i]; 83 | str[i] = str[length - 1 - i]; 84 | str[length - 1 - i] = temp; 85 | } 86 | } 87 | 88 | // ==================== Test Code ==================== 89 | void test(char* testName, char* num1, char* num2, char* sum, char* expected, int valid) 90 | { 91 | int result; 92 | 93 | if(testName != NULL) 94 | printf("%s begins: ", testName); 95 | 96 | result = add(num1, num2, sum); 97 | if((result == -1 && valid == -1) || (valid == 0 && strcmp(sum, expected) == 0)) 98 | printf("Passed.\n"); 99 | else 100 | printf("Failed.\n"); 101 | } 102 | 103 | void test1() 104 | { 105 | char num1[] = "999"; 106 | char num2[] = "3"; 107 | char sum[20]; 108 | char* expected = "1002"; 109 | test("Test1", num1, num2, sum, expected, 0); 110 | } 111 | 112 | void test2() 113 | { 114 | char num1[] = "33"; 115 | char num2[] = "9999"; 116 | char sum[20]; 117 | char* expected = "10032"; 118 | test("Test2", num1, num2, sum, expected, 0); 119 | } 120 | 121 | void test3() 122 | { 123 | char num1[] = "3333333"; 124 | char num2[] = "222"; 125 | char sum[20]; 126 | char* expected = "3333555"; 127 | test("Test3", num1, num2, sum, expected, 0); 128 | } 129 | 130 | void test4() 131 | { 132 | char num1[] = "33abc33"; 133 | char num2[] = "222"; 134 | char sum[20]; 135 | char* expected = ""; 136 | test("Test4", num1, num2, sum, expected, -1); 137 | } 138 | 139 | void test5() 140 | { 141 | test("Test5", NULL, NULL, NULL, NULL, -1); 142 | } 143 | 144 | void test6() 145 | { 146 | char num1[] = "3333333344445555"; 147 | char num2[] = "222222222222222"; 148 | char sum[20]; 149 | char* expected = "3555555566667777"; 150 | test("Test6", num1, num2, sum, expected, 0); 151 | } 152 | 153 | int main(int argc, char* argv[]) 154 | { 155 | test1(); 156 | test2(); 157 | test3(); 158 | test4(); 159 | test5(); 160 | test6(); 161 | 162 | return 0; 163 | } 164 | -------------------------------------------------------------------------------- /045_ReorderNumbers.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | public class ReorderNumbers { 5 | //================= Solution 1 ================= 6 | public static void reorderOddEven_solution1(int nums[]) { 7 | int begin = 0; 8 | int end = nums.length - 1; 9 | while(begin < end) { 10 | // Move begin forwards until it meets an even number 11 | while(begin < end && (nums[begin] & 0x1) != 0) 12 | begin++; 13 | 14 | // Move end backwards until it meets an odd number 15 | while(begin < end && (nums[end] & 0x1) == 0) 16 | end--; 17 | 18 | if(begin < end) { 19 | int temp = nums[begin]; 20 | nums[begin] = nums[end]; 21 | nums[end] = temp; 22 | } 23 | } 24 | } 25 | 26 | //================= Solution 2 ================= 27 | public static void reorderOddEven_solution2(int nums[]) { 28 | Criterion isEven = new Criterion() { 29 | public boolean check(int num) { 30 | if((num & 0x1) == 0) 31 | return true; 32 | 33 | return false; 34 | } 35 | }; 36 | 37 | reorder(nums, isEven); 38 | } 39 | 40 | public interface Criterion{ 41 | boolean check(int num); 42 | } 43 | 44 | private static void reorder(int nums[], Criterion criterion) { 45 | int begin = 0; 46 | int end = nums.length - 1; 47 | while(begin < end) { 48 | while(begin < end && !criterion.check(nums[begin])) 49 | begin++; 50 | 51 | while(begin < end && criterion.check(nums[end])) 52 | end--; 53 | 54 | if(begin < end) { 55 | int temp = nums[begin]; 56 | nums[begin] = nums[end]; 57 | nums[end] = temp; 58 | } 59 | } 60 | } 61 | 62 | //================= Test Code ================= 63 | private static void test(String testName, int nums[]) { 64 | System.out.print(testName + " begins: "); 65 | 66 | int copy[] = new int[nums.length]; 67 | for(int i = 0; i < nums.length; ++i) 68 | copy[i] = nums[i]; 69 | 70 | reorderOddEven_solution1(nums); 71 | if(checkOddBeforeEven(nums)) 72 | System.out.print("Solution1 Passed; "); 73 | else 74 | System.out.print("Solution1 FAILED; "); 75 | 76 | reorderOddEven_solution2(copy); 77 | if(checkOddBeforeEven(copy)) 78 | System.out.print("Solution2 Passed.\n"); 79 | else 80 | System.out.print("Solution2 FAILED.\n"); 81 | } 82 | 83 | private static boolean checkOddBeforeEven(int nums[]) { 84 | int i = 0; 85 | while(i < nums.length) { 86 | if((nums[i] & 0x01) == 0) 87 | break; 88 | 89 | ++i; 90 | } 91 | 92 | while(i < nums.length) { 93 | if((nums[i] & 0x01) == 1) 94 | break; 95 | 96 | ++i; 97 | } 98 | 99 | return (i == nums.length); 100 | } 101 | 102 | private static void test1() { 103 | int nums[] = {1, 2, 3, 4, 5, 6, 7}; 104 | test("Test1", nums); 105 | } 106 | 107 | private static void test2() { 108 | int nums[] = {2, 4, 6, 1, 3, 5, 7}; 109 | test("Test2", nums); 110 | } 111 | 112 | private static void test3() { 113 | int nums[] = {1, 3, 5, 7, 2, 4, 6}; 114 | test("Test3", nums); 115 | } 116 | 117 | private static void test4() { 118 | int nums[] = {1}; 119 | test("Test4", nums); 120 | } 121 | 122 | private static void test5() { 123 | int nums[] = {2}; 124 | test("Test5", nums); 125 | } 126 | 127 | public static void main(String args[]) { 128 | test1(); 129 | test2(); 130 | test3(); 131 | test4(); 132 | test5(); 133 | } 134 | } 135 | -------------------------------------------------------------------------------- /081_ReversedPairs.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | public class ReversedPairs { 5 | public static int countReversedPairs(int[] numbers) { 6 | int[] buffer = new int[numbers.length]; 7 | return countReversedPairs(numbers, buffer, 0, numbers.length - 1); 8 | } 9 | 10 | private static int countReversedPairs(int[] numbers, int[] buffer, int start, int end) { 11 | if(start >= end) 12 | return 0; 13 | 14 | int middle = start + (end - start) / 2; 15 | 16 | int left = countReversedPairs(numbers, buffer, start, middle); 17 | int right = countReversedPairs(numbers, buffer, middle + 1, end); 18 | int between = merge(numbers, buffer, start, middle, end); 19 | 20 | return left + right + between; 21 | } 22 | 23 | private static int merge(int[] numbers, int[] buffer, int start, int middle, int end) { 24 | int i = middle; // the end of the first sub-array 25 | int j = end; // the end of the second sub-array 26 | int k = end; // the end of the merged array 27 | int count = 0; 28 | while(i >= start && j >= middle + 1) { 29 | if(numbers[i] > numbers[j]) { 30 | buffer[k--] = numbers[i--]; 31 | count += (j - middle); 32 | } 33 | else { 34 | buffer[k--] = numbers[j--]; 35 | } 36 | } 37 | 38 | while(i >= start) { 39 | buffer[k--] = numbers[i--]; 40 | } 41 | 42 | while(j >= middle + 1) { 43 | buffer[k--] = numbers[j--]; 44 | } 45 | 46 | // copy elements from buffer[] to numbers[] 47 | for(i = start; i <= end; ++i) { 48 | numbers[i] = buffer[i]; 49 | } 50 | 51 | return count; 52 | } 53 | 54 | //================= Test Code ================= 55 | 56 | private static void test(String testName, int[] numbers, int expected) { 57 | System.out.print(testName + " begins: "); 58 | 59 | if(countReversedPairs(numbers) == expected) 60 | System.out.print("passed.\n"); 61 | else 62 | System.out.print("FAILED.\n"); 63 | } 64 | 65 | private static void test1() { 66 | int[] numbers = {1, 2, 3, 4, 7, 6, 5}; 67 | int expected = 3; 68 | test("Test1", numbers, expected); 69 | } 70 | 71 | // decreasingly sorted array 72 | private static void test2() { 73 | int[] numbers = {6, 5, 4, 3, 2, 1}; 74 | int expected = 15; 75 | test("Test2", numbers, expected); 76 | } 77 | 78 | // increasingly sorted array 79 | private static void test3() { 80 | int[] numbers = {1, 2, 3, 4, 5, 6}; 81 | int expected = 0; 82 | test("Test3", numbers, expected); 83 | } 84 | 85 | // only one number 86 | private static void test4() { 87 | int[] numbers = {1}; 88 | int expected = 0; 89 | test("Test4", numbers, expected); 90 | } 91 | 92 | // two numbers 93 | private static void test5() { 94 | int[] numbers = {1, 2}; 95 | int expected = 0; 96 | test("Test5", numbers, expected); 97 | } 98 | 99 | // two numbers 100 | private static void test6() { 101 | int[] numbers = {2, 1}; 102 | int expected = 1; 103 | test("Test5", numbers, expected); 104 | } 105 | 106 | // duplicated numbers 107 | private static void test7() { 108 | int[] numbers = {1, 2, 1, 2, 1}; 109 | int expected = 3; 110 | test("Test7", numbers, expected); 111 | } 112 | 113 | // duplicated numbers 114 | private static void test8() { 115 | int[] numbers = {7, 5, 4, 5, 3, 5, 6, 5}; 116 | int expected = 12; 117 | test("Test8", numbers, expected); 118 | } 119 | 120 | public static void main(String[] argv) { 121 | test1(); 122 | test2(); 123 | test3(); 124 | test4(); 125 | test5(); 126 | test6(); 127 | test7(); 128 | test8(); 129 | } 130 | } 131 | -------------------------------------------------------------------------------- /046_RemoveNumbers.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | public class RemoveNumbers { 5 | public static int remove_solution1(int numbers[], int n) { 6 | int i = 0; 7 | for (int j = 0; j < numbers.length; j++) { 8 | if (numbers[j] != n) 9 | numbers[i++] = numbers[j]; 10 | } 11 | 12 | return i; 13 | } 14 | 15 | public static int remove_solution2(int numbers[], int n) { 16 | int p1 = 0; 17 | while(p1 < numbers.length && numbers[p1] != n) 18 | ++p1; 19 | 20 | int p2 = numbers.length - 1; 21 | while(p1 < p2){ 22 | while(p1 < numbers.length && numbers[p1] != n) 23 | ++p1; 24 | while(p2 > 0 && numbers[p2] == n) 25 | --p2; 26 | 27 | if(p1 < p2){ 28 | numbers[p1] = numbers[p2]; 29 | numbers[p2] = n; 30 | } 31 | } 32 | 33 | return p1; 34 | } 35 | 36 | //================= Test Code ================= 37 | private static boolean checkRemoved(int numbers[], int n, int expected) { 38 | int i = 0; 39 | while(i < expected) 40 | { 41 | if(numbers[i] == n) 42 | break; 43 | 44 | ++i; 45 | } 46 | 47 | return (i == expected); 48 | } 49 | 50 | private static void test(String testName, int nums[], int n, int expected) { 51 | System.out.print(testName + " begins: "); 52 | 53 | int copy[] = new int[nums.length]; 54 | for(int i = 0; i < nums.length; ++i) 55 | copy[i] = nums[i]; 56 | 57 | int result1 = remove_solution1(nums, n); 58 | if((result1 == expected) && checkRemoved(nums, n, expected)) 59 | System.out.print("Solution1 Passed; "); 60 | else 61 | System.out.print("Solution1 FAILED; "); 62 | 63 | int result2 = remove_solution2(copy, n); 64 | if((result2 == expected) && checkRemoved(copy, n, expected)) 65 | System.out.print("Solution2 Passed.\n"); 66 | else 67 | System.out.print("Solution2 FAILED.\n"); 68 | } 69 | 70 | // multiple targets to be deleted 71 | private static void test1() { 72 | int numbers[] = {4, 3, 2, 1, 2, 3, 6}; 73 | int n = 2; 74 | int expected = 5; 75 | 76 | test("Test1", numbers, n, expected); 77 | } 78 | 79 | // targets are the first and last elements 80 | private static void test2() { 81 | int numbers[] = {4, 3, 2, 1, 2, 3, 4}; 82 | int n = 4; 83 | int expected = 5; 84 | 85 | test("Test2", numbers, n, expected); 86 | } 87 | 88 | // all elements are targets to be deleted 89 | private static void test3() { 90 | int numbers[] = {4, 4, 4, 4}; 91 | int n = 4; 92 | int expected = 0; 93 | 94 | test("Test3", numbers, n, expected); 95 | } 96 | 97 | // no target to be deleted 98 | private static void test4() { 99 | int numbers[] = {4, 3, 2, 1, 2, 3, 6}; 100 | int n = 5; 101 | int expected = 7; 102 | 103 | test("Test4", numbers, n, expected); 104 | } 105 | 106 | // the only number is the target 107 | private static void test5() { 108 | int numbers[] = {4}; 109 | int n = 4; 110 | int expected = 0; 111 | 112 | test("Test5", numbers, n, expected); 113 | } 114 | 115 | // the only number is the target 116 | private static void test6() { 117 | int numbers[] = {4}; 118 | int n = 5; 119 | int expected = 1; 120 | 121 | test("Test6", numbers, n, expected); 122 | } 123 | 124 | // all elements except one are targets to be deleted 125 | private static void test7() { 126 | int numbers[] = {4, 4, 3, 4}; 127 | int n = 4; 128 | int expected = 1; 129 | 130 | test("Test7", numbers, n, expected); 131 | } 132 | 133 | public static void main(String args[]) { 134 | test1(); 135 | test2(); 136 | test3(); 137 | test4(); 138 | test5(); 139 | test6(); 140 | test7(); 141 | } 142 | } 143 | -------------------------------------------------------------------------------- /047_KthNodeFromEnd.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include "..\Utility\List.h" 6 | 7 | ListNode* FindKthToTail(ListNode* pListHead, unsigned int k) 8 | { 9 | if(pListHead == NULL || k == 0) 10 | return NULL; 11 | 12 | ListNode *pAhead = pListHead; 13 | ListNode *pBehind = NULL; 14 | 15 | for(unsigned int i = 0; i < k - 1; ++ i) 16 | { 17 | if(pAhead->m_pNext != NULL) 18 | pAhead = pAhead->m_pNext; 19 | else 20 | { 21 | return NULL; 22 | } 23 | } 24 | 25 | pBehind = pListHead; 26 | while(pAhead->m_pNext != NULL) 27 | { 28 | pAhead = pAhead->m_pNext; 29 | pBehind = pBehind->m_pNext; 30 | } 31 | 32 | return pBehind; 33 | } 34 | 35 | // ==================== Test Code ==================== 36 | void Test(char* testName, ListNode* pHead, int index, int expected, bool isNull) 37 | { 38 | if(testName != NULL) 39 | printf("%s begins: ", testName); 40 | 41 | ListNode* pNode = FindKthToTail(pHead, index); 42 | if((isNull && pNode == NULL) || (!isNull && (pNode->m_nValue == expected))) 43 | printf("Passed.\n"); 44 | else 45 | printf("FAILED.\n"); 46 | } 47 | 48 | // The target node is inside the list 49 | void Test1() 50 | { 51 | ListNode* pNode1 = CreateListNode(1); 52 | ListNode* pNode2 = CreateListNode(2); 53 | ListNode* pNode3 = CreateListNode(3); 54 | ListNode* pNode4 = CreateListNode(4); 55 | ListNode* pNode5 = CreateListNode(5); 56 | 57 | ConnectListNodes(pNode1, pNode2); 58 | ConnectListNodes(pNode2, pNode3); 59 | ConnectListNodes(pNode3, pNode4); 60 | ConnectListNodes(pNode4, pNode5); 61 | 62 | Test("Test1", pNode1, 2, 4, false); 63 | 64 | DestroyList(pNode1); 65 | } 66 | 67 | // The target node is the tail node 68 | void Test2() 69 | { 70 | ListNode* pNode1 = CreateListNode(1); 71 | ListNode* pNode2 = CreateListNode(2); 72 | ListNode* pNode3 = CreateListNode(3); 73 | ListNode* pNode4 = CreateListNode(4); 74 | ListNode* pNode5 = CreateListNode(5); 75 | 76 | ConnectListNodes(pNode1, pNode2); 77 | ConnectListNodes(pNode2, pNode3); 78 | ConnectListNodes(pNode3, pNode4); 79 | ConnectListNodes(pNode4, pNode5); 80 | 81 | Test("Test2", pNode1, 1, 5, false); 82 | 83 | DestroyList(pNode1); 84 | } 85 | 86 | // The target node is the head node 87 | void Test3() 88 | { 89 | ListNode* pNode1 = CreateListNode(1); 90 | ListNode* pNode2 = CreateListNode(2); 91 | ListNode* pNode3 = CreateListNode(3); 92 | ListNode* pNode4 = CreateListNode(4); 93 | ListNode* pNode5 = CreateListNode(5); 94 | 95 | ConnectListNodes(pNode1, pNode2); 96 | ConnectListNodes(pNode2, pNode3); 97 | ConnectListNodes(pNode3, pNode4); 98 | ConnectListNodes(pNode4, pNode5); 99 | 100 | Test("Test3", pNode1, 5, 1, false); 101 | 102 | DestroyList(pNode1); 103 | } 104 | 105 | // empty list 106 | void Test4() 107 | { 108 | Test("Test4", NULL, 100, 1, true); 109 | } 110 | 111 | // the input k is greater than the number of nodes in a list 112 | void Test5() 113 | { 114 | ListNode* pNode1 = CreateListNode(1); 115 | ListNode* pNode2 = CreateListNode(2); 116 | ListNode* pNode3 = CreateListNode(3); 117 | ListNode* pNode4 = CreateListNode(4); 118 | ListNode* pNode5 = CreateListNode(5); 119 | 120 | ConnectListNodes(pNode1, pNode2); 121 | ConnectListNodes(pNode2, pNode3); 122 | ConnectListNodes(pNode3, pNode4); 123 | ConnectListNodes(pNode4, pNode5); 124 | 125 | Test("Test5", pNode1, 6, 1, true); 126 | 127 | DestroyList(pNode1); 128 | } 129 | 130 | // the input k is 0 131 | void Test6() 132 | { 133 | ListNode* pNode1 = CreateListNode(1); 134 | ListNode* pNode2 = CreateListNode(2); 135 | ListNode* pNode3 = CreateListNode(3); 136 | ListNode* pNode4 = CreateListNode(4); 137 | ListNode* pNode5 = CreateListNode(5); 138 | 139 | ConnectListNodes(pNode1, pNode2); 140 | ConnectListNodes(pNode2, pNode3); 141 | ConnectListNodes(pNode3, pNode4); 142 | ConnectListNodes(pNode4, pNode5); 143 | 144 | Test("Test6", pNode1, 0, 1, true); 145 | 146 | DestroyList(pNode1); 147 | } 148 | 149 | int main(int argc, char* argv[]) 150 | { 151 | Test1(); 152 | Test2(); 153 | Test3(); 154 | Test4(); 155 | Test5(); 156 | Test6(); 157 | 158 | return 0; 159 | } 160 | -------------------------------------------------------------------------------- /053_PrintMatrix.java: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | public class PrintMatrix { 5 | public static void printMatrixClockwise(int numbers[][]) { 6 | int rows = numbers.length; 7 | int columns = numbers[0].length; 8 | int start = 0; 9 | 10 | while(columns > start * 2 && rows > start * 2) { 11 | printRing(numbers, start); 12 | 13 | ++start; 14 | } 15 | } 16 | 17 | private static void printRing(int numbers[][], int start) 18 | { 19 | int rows = numbers.length; 20 | int columns = numbers[0].length; 21 | int endX = columns - 1 - start; 22 | int endY = rows - 1 - start; 23 | 24 | // Print a row from left to right 25 | for(int i = start; i <= endX; ++i) { 26 | int number = numbers[start][i]; 27 | printNumber(number); 28 | } 29 | 30 | // print a column top down 31 | if(start < endY) { 32 | for(int i = start + 1; i <= endY; ++i) { 33 | int number = numbers[i][endX]; 34 | printNumber(number); 35 | } 36 | } 37 | 38 | // print a row from right to left 39 | if(start < endX && start < endY) { 40 | for(int i = endX - 1; i >= start; --i) { 41 | int number = numbers[endY][i]; 42 | printNumber(number); 43 | } 44 | } 45 | 46 | // print a column bottom up 47 | if(start < endX && start < endY - 1) { 48 | for(int i = endY - 1; i >= start + 1; --i) { 49 | int number = numbers[i][start]; 50 | printNumber(number); 51 | } 52 | } 53 | } 54 | 55 | private static void printNumber(int number) { 56 | System.out.print(number); 57 | System.out.print("\t"); 58 | } 59 | 60 | //================= Test Code ================= 61 | private static void test(int columns, int rows) 62 | { 63 | System.out.print("Test Begin: "); 64 | System.out.print(columns); 65 | System.out.print(" columns, "); 66 | System.out.print(rows); 67 | System.out.print(" rows.\n"); 68 | 69 | if(columns < 1 || rows < 1) 70 | return; 71 | 72 | int numbers[][] = new int[rows][]; 73 | for(int i = 0; i < rows; ++i) { 74 | numbers[i] = new int[columns]; 75 | for(int j = 0; j < columns; ++j) { 76 | numbers[i][j] = i * columns + j + 1; 77 | } 78 | } 79 | 80 | printMatrixClockwise(numbers); 81 | System.out.print("\n"); 82 | } 83 | 84 | public static void main(String[] args) { 85 | /* 86 | 1 87 | */ 88 | test(1, 1); 89 | 90 | /* 91 | 1 2 92 | 3 4 93 | */ 94 | test(2, 2); 95 | 96 | /* 97 | 1 2 3 4 98 | 5 6 7 8 99 | 9 10 11 12 100 | 13 14 15 16 101 | */ 102 | test(4, 4); 103 | 104 | /* 105 | 1 2 3 4 5 106 | 6 7 8 9 10 107 | 11 12 13 14 15 108 | 16 17 18 19 20 109 | 21 22 23 24 25 110 | */ 111 | test(5, 5); 112 | 113 | /* 114 | 1 115 | 2 116 | 3 117 | 4 118 | 5 119 | */ 120 | test(1, 5); 121 | 122 | /* 123 | 1 2 124 | 3 4 125 | 5 6 126 | 7 8 127 | 9 10 128 | */ 129 | test(2, 5); 130 | 131 | /* 132 | 1 2 3 133 | 4 5 6 134 | 7 8 9 135 | 10 11 12 136 | 13 14 15 137 | */ 138 | test(3, 5); 139 | 140 | /* 141 | 1 2 3 4 142 | 5 6 7 8 143 | 9 10 11 12 144 | 13 14 15 16 145 | 17 18 19 20 146 | */ 147 | test(4, 5); 148 | 149 | /* 150 | 1 2 3 4 5 151 | */ 152 | test(5, 1); 153 | 154 | /* 155 | 1 2 3 4 5 156 | 6 7 8 9 10 157 | */ 158 | test(5, 2); 159 | 160 | /* 161 | 1 2 3 4 5 162 | 6 7 8 9 10 163 | 11 12 13 14 15 164 | */ 165 | test(5, 3); 166 | 167 | /* 168 | 1 2 3 4 5 169 | 6 7 8 9 10 170 | 11 12 13 14 15 171 | 16 17 18 19 20 172 | */ 173 | test(5, 4); 174 | } 175 | } 176 | -------------------------------------------------------------------------------- /016_LoopsInLists.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include "../Utility/list.h" 6 | 7 | bool HasLoop(ListNode* pHead) 8 | { 9 | if(pHead == NULL) 10 | return false; 11 | 12 | ListNode* pSlow = pHead->m_pNext; 13 | if(pSlow == NULL) 14 | return false; 15 | 16 | ListNode* pFast = pSlow->m_pNext; 17 | while(pFast != NULL && pSlow != NULL) 18 | { 19 | if(pFast == pSlow) 20 | return true; 21 | 22 | pSlow = pSlow->m_pNext; 23 | 24 | pFast = pFast->m_pNext; 25 | if(pFast != NULL) 26 | pFast = pFast->m_pNext; 27 | } 28 | 29 | return false; 30 | } 31 | 32 | // ==================== Test Code ==================== 33 | void Test(char* testName, ListNode* pHead, bool expected) 34 | { 35 | if(testName != NULL) 36 | printf("%s begins: ", testName); 37 | 38 | if(HasLoop(pHead) == expected) 39 | printf("HasLoop Passed.\n"); 40 | else 41 | printf("HasLoop FAILED.\n"); 42 | } 43 | 44 | // A list has a node, without a loop 45 | void Test1() 46 | { 47 | ListNode* pNode1 = CreateListNode(1); 48 | 49 | Test("Test1", pNode1, false); 50 | 51 | DestroyList(pNode1); 52 | } 53 | 54 | // A list has a node, with a loop 55 | void Test2() 56 | { 57 | ListNode* pNode1 = CreateListNode(1); 58 | ConnectListNodes(pNode1, pNode1); 59 | 60 | Test("Test2", pNode1, true); 61 | 62 | delete pNode1; 63 | pNode1 = NULL; 64 | } 65 | 66 | // A list has multiple nodes, with a loop 67 | void Test3() 68 | { 69 | ListNode* pNode1 = CreateListNode(1); 70 | ListNode* pNode2 = CreateListNode(2); 71 | ListNode* pNode3 = CreateListNode(3); 72 | ListNode* pNode4 = CreateListNode(4); 73 | ListNode* pNode5 = CreateListNode(5); 74 | 75 | ConnectListNodes(pNode1, pNode2); 76 | ConnectListNodes(pNode2, pNode3); 77 | ConnectListNodes(pNode3, pNode4); 78 | ConnectListNodes(pNode4, pNode5); 79 | ConnectListNodes(pNode5, pNode3); 80 | 81 | Test("Test3", pNode1, true); 82 | 83 | delete pNode1; 84 | pNode1 = NULL; 85 | delete pNode2; 86 | pNode2 = NULL; 87 | delete pNode3; 88 | pNode3 = NULL; 89 | delete pNode4; 90 | pNode4 = NULL; 91 | delete pNode5; 92 | pNode5 = NULL; 93 | } 94 | 95 | // A list has multiple nodes, with a loop 96 | void Test4() 97 | { 98 | ListNode* pNode1 = CreateListNode(1); 99 | ListNode* pNode2 = CreateListNode(2); 100 | ListNode* pNode3 = CreateListNode(3); 101 | ListNode* pNode4 = CreateListNode(4); 102 | ListNode* pNode5 = CreateListNode(5); 103 | 104 | ConnectListNodes(pNode1, pNode2); 105 | ConnectListNodes(pNode2, pNode3); 106 | ConnectListNodes(pNode3, pNode4); 107 | ConnectListNodes(pNode4, pNode5); 108 | ConnectListNodes(pNode5, pNode1); 109 | 110 | Test("Test4", pNode1, true); 111 | 112 | delete pNode1; 113 | pNode1 = NULL; 114 | delete pNode2; 115 | pNode2 = NULL; 116 | delete pNode3; 117 | pNode3 = NULL; 118 | delete pNode4; 119 | pNode4 = NULL; 120 | delete pNode5; 121 | pNode5 = NULL; 122 | } 123 | 124 | // A list has multiple nodes, with a loop 125 | void Test5() 126 | { 127 | ListNode* pNode1 = CreateListNode(1); 128 | ListNode* pNode2 = CreateListNode(2); 129 | ListNode* pNode3 = CreateListNode(3); 130 | ListNode* pNode4 = CreateListNode(4); 131 | ListNode* pNode5 = CreateListNode(5); 132 | 133 | ConnectListNodes(pNode1, pNode2); 134 | ConnectListNodes(pNode2, pNode3); 135 | ConnectListNodes(pNode3, pNode4); 136 | ConnectListNodes(pNode4, pNode5); 137 | ConnectListNodes(pNode5, pNode5); 138 | 139 | Test("Test5", pNode1, true); 140 | 141 | delete pNode1; 142 | pNode1 = NULL; 143 | delete pNode2; 144 | pNode2 = NULL; 145 | delete pNode3; 146 | pNode3 = NULL; 147 | delete pNode4; 148 | pNode4 = NULL; 149 | delete pNode5; 150 | pNode5 = NULL; 151 | } 152 | 153 | // A list has multiple nodes, without a loop 154 | void Test6() 155 | { 156 | ListNode* pNode1 = CreateListNode(1); 157 | ListNode* pNode2 = CreateListNode(2); 158 | ListNode* pNode3 = CreateListNode(3); 159 | ListNode* pNode4 = CreateListNode(4); 160 | ListNode* pNode5 = CreateListNode(5); 161 | 162 | ConnectListNodes(pNode1, pNode2); 163 | ConnectListNodes(pNode2, pNode3); 164 | ConnectListNodes(pNode3, pNode4); 165 | ConnectListNodes(pNode4, pNode5); 166 | 167 | Test("Test6", pNode1, false); 168 | 169 | DestroyList(pNode1); 170 | } 171 | 172 | // Empty list 173 | void Test7() 174 | { 175 | Test("Test7", NULL, false); 176 | } 177 | 178 | int main(int argc, char* argv[]) 179 | { 180 | Test1(); 181 | Test2(); 182 | Test3(); 183 | Test4(); 184 | Test5(); 185 | Test6(); 186 | Test7(); 187 | 188 | return 0; 189 | } 190 | -------------------------------------------------------------------------------- /049_ReverseListInGroups.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include "../Utility/list.h" 6 | 7 | void ReverseGroup(ListNode* pNode1, ListNode* pNode2); 8 | 9 | ListNode* Reverse(ListNode* pHead, unsigned int k) 10 | { 11 | if(pHead == NULL || k <= 1) 12 | return pHead; 13 | 14 | ListNode* pReversedHead = NULL; 15 | ListNode* pNode1 = pHead; 16 | ListNode* pPrev = NULL; 17 | while(pNode1 != NULL) 18 | { 19 | // find k nodes within a group 20 | ListNode* pNode2 = pNode1; 21 | ListNode* pNext = NULL; 22 | for(unsigned int i = 1; pNode2->m_pNext != NULL && i < k; ++i) 23 | pNode2 = pNode2->m_pNext; 24 | 25 | pNext = pNode2->m_pNext; 26 | 27 | // reverse nodes within a group 28 | ReverseGroup(pNode1, pNode2); 29 | 30 | // connect groups together 31 | if(pReversedHead == NULL) 32 | pReversedHead = pNode2; 33 | 34 | if(pPrev != NULL) 35 | pPrev->m_pNext = pNode2; 36 | pPrev = pNode1; 37 | pNode1 = pNext; 38 | } 39 | 40 | return pReversedHead; 41 | } 42 | 43 | void ReverseGroup(ListNode* pNode1, ListNode* pNode2) 44 | { 45 | ListNode* pNode = pNode1; 46 | ListNode* pPrev = NULL; 47 | while(pNode != pNode2) 48 | { 49 | ListNode* pNext = pNode->m_pNext; 50 | pNode->m_pNext = pPrev; 51 | 52 | pPrev = pNode; 53 | pNode = pNext; 54 | } 55 | 56 | pNode->m_pNext = pPrev; 57 | } 58 | 59 | // ==================== Test Code ==================== 60 | ListNode* Test(char* testName, ListNode* pHead, unsigned int k) 61 | { 62 | if(testName != NULL) 63 | printf("====%s begins: ====\n", testName); 64 | 65 | printf("The original list is: "); 66 | PrintList(pHead); 67 | 68 | printf("The reversed list is: "); 69 | ListNode* pReversedHead = Reverse(pHead, k); 70 | PrintList(pReversedHead); 71 | 72 | printf("\n\n"); 73 | 74 | return pReversedHead; 75 | } 76 | 77 | ListNode* BuildList() 78 | { 79 | ListNode* pNode1 = CreateListNode(1); 80 | ListNode* pNode2 = CreateListNode(2); 81 | ListNode* pNode3 = CreateListNode(3); 82 | ListNode* pNode4 = CreateListNode(4); 83 | ListNode* pNode5 = CreateListNode(5); 84 | ListNode* pNode6 = CreateListNode(6); 85 | ListNode* pNode7 = CreateListNode(7); 86 | ListNode* pNode8 = CreateListNode(8); 87 | 88 | ConnectListNodes(pNode1, pNode2); 89 | ConnectListNodes(pNode2, pNode3); 90 | ConnectListNodes(pNode3, pNode4); 91 | ConnectListNodes(pNode4, pNode5); 92 | ConnectListNodes(pNode5, pNode6); 93 | ConnectListNodes(pNode6, pNode7); 94 | ConnectListNodes(pNode7, pNode8); 95 | 96 | return pNode1; 97 | } 98 | 99 | void Test1() 100 | { 101 | ListNode* pHead = BuildList(); 102 | ListNode* pReversedHead = Test("Test1", pHead, 1); 103 | 104 | DestroyList(pReversedHead); 105 | } 106 | 107 | void Test2() 108 | { 109 | ListNode* pHead = BuildList(); 110 | ListNode* pReversedHead = Test("Test2", pHead, 2); 111 | 112 | DestroyList(pReversedHead); 113 | } 114 | 115 | void Test3() 116 | { 117 | ListNode* pHead = BuildList(); 118 | ListNode* pReversedHead = Test("Test3", pHead, 3); 119 | 120 | DestroyList(pReversedHead); 121 | } 122 | 123 | void Test4() 124 | { 125 | ListNode* pHead = BuildList(); 126 | ListNode* pReversedHead = Test("Test4", pHead, 4); 127 | 128 | DestroyList(pReversedHead); 129 | } 130 | 131 | void Test5() 132 | { 133 | ListNode* pHead = BuildList(); 134 | ListNode* pReversedHead = Test("Test5", pHead, 5); 135 | 136 | DestroyList(pReversedHead); 137 | } 138 | 139 | void Test6() 140 | { 141 | ListNode* pHead = BuildList(); 142 | ListNode* pReversedHead = Test("Test6", pHead, 6); 143 | 144 | DestroyList(pReversedHead); 145 | } 146 | 147 | void Test7() 148 | { 149 | ListNode* pHead = BuildList(); 150 | ListNode* pReversedHead = Test("Test7", pHead, 7); 151 | 152 | DestroyList(pReversedHead); 153 | } 154 | 155 | void Test8() 156 | { 157 | ListNode* pHead = BuildList(); 158 | ListNode* pReversedHead = Test("Test8", pHead, 8); 159 | 160 | DestroyList(pReversedHead); 161 | } 162 | 163 | void Test9() 164 | { 165 | ListNode* pHead = BuildList(); 166 | ListNode* pReversedHead = Test("Test9", pHead, 9); 167 | 168 | DestroyList(pReversedHead); 169 | } 170 | 171 | void Test10() 172 | { 173 | ListNode* pHead = NULL; 174 | ListNode* pReversedHead = Test("Test10", pHead, 0); 175 | 176 | DestroyList(pReversedHead); 177 | } 178 | 179 | int main(int argc, char* argv[]) 180 | { 181 | Test1(); 182 | Test2(); 183 | Test3(); 184 | Test4(); 185 | Test5(); 186 | Test6(); 187 | Test7(); 188 | Test8(); 189 | Test9(); 190 | Test10(); 191 | 192 | return 0; 193 | } 194 | 195 | -------------------------------------------------------------------------------- /071_ArrayIntersection.cpp: -------------------------------------------------------------------------------- 1 | // Coding Interviews: Questions, Analysis & Solutions 2 | // Harry He 3 | 4 | #include 5 | #include 6 | #include 7 | 8 | using namespace std; 9 | 10 | // ==================== Solution 1 ==================== 11 | void GetIntersection_solution1(const vector& array1, 12 | const vector& array2, 13 | vector& intersection) 14 | { 15 | vector::const_iterator iter1 = array1.begin(); 16 | vector::const_iterator iter2 = array2.begin(); 17 | 18 | intersection.clear(); 19 | 20 | while(iter1 != array1.end() && iter2 != array2.end()) 21 | { 22 | if(*iter1 == *iter2) 23 | { 24 | intersection.push_back(*iter1); 25 | ++ iter1; 26 | ++ iter2; 27 | } 28 | else if(*iter1 < *iter2) 29 | ++ iter1; 30 | else 31 | ++ iter2; 32 | } 33 | } 34 | 35 | // ==================== Solution 2 ==================== 36 | /* === Supposing array1 is much longer than array2 === */ 37 | void GetIntersection_solution2(const vector& array1, 38 | const vector& array2, 39 | vector& intersection) 40 | { 41 | intersection.clear(); 42 | 43 | vector::const_iterator iter1 = array1.begin(); 44 | while(iter1 != array1.end()) 45 | { 46 | if(binary_search(array2.begin(), array2.end(), *iter1)) 47 | intersection.push_back(*iter1); 48 | } 49 | } 50 | 51 | // ==================== Test Code ==================== 52 | bool CheckIdenticalArray(const vector& array1, 53 | const vector& array2) 54 | { 55 | vector::const_iterator iter1 = array1.begin(); 56 | vector::const_iterator iter2 = array2.begin(); 57 | 58 | bool identical = true; 59 | while(iter1 != array1.end() && iter2 != array2.end()) 60 | { 61 | if(*iter1 != *iter2) 62 | { 63 | identical = false; 64 | break; 65 | } 66 | 67 | ++ iter1; 68 | ++ iter2; 69 | } 70 | 71 | if(iter1 != array1.end() || iter2 != array2.end()) 72 | identical = false; 73 | 74 | return identical; 75 | } 76 | 77 | void Test(char* testName, 78 | const vector& array1, 79 | const vector& array2, 80 | vector& expected) 81 | { 82 | if(testName != NULL) 83 | printf("%s begins: ", testName); 84 | 85 | vector result1; 86 | GetIntersection_solution1(array1, array2, result1); 87 | if(CheckIdenticalArray(result1, expected)) 88 | printf("solution1 passed; "); 89 | else 90 | printf("solution1 FAILED; "); 91 | 92 | vector result2; 93 | GetIntersection_solution1(array1, array2, result2); 94 | if(CheckIdenticalArray(result2, expected)) 95 | printf("solution2 passed.\n"); 96 | else 97 | printf("solution2 FAILED.\n"); 98 | } 99 | 100 | void Test1() 101 | { 102 | int numbers1[] = {1, 4, 7, 10, 13, 16}; 103 | vector array1(numbers1, numbers1 + sizeof(numbers1) / sizeof(int)); 104 | 105 | int numbers2[] = {1, 3, 5, 7, 9, 11}; 106 | vector array2(numbers2, numbers2 + sizeof(numbers2) / sizeof(int)); 107 | 108 | int exp[] = {1, 7}; 109 | vector expected(exp, exp + sizeof(exp) / sizeof(int)); 110 | 111 | Test("Test1", array1, array2, expected); 112 | } 113 | 114 | void Test2() 115 | { 116 | int numbers1[] = {4, 7, 10, 13}; 117 | vector array1(numbers1, numbers1 + sizeof(numbers1) / sizeof(int)); 118 | 119 | int numbers2[] = {1, 3, 5, 7, 9, 11, 13}; 120 | vector array2(numbers2, numbers2 + sizeof(numbers2) / sizeof(int)); 121 | 122 | int exp[] = {7, 13}; 123 | vector expected(exp, exp + sizeof(exp) / sizeof(int)); 124 | 125 | Test("Test2", array1, array2, expected); 126 | } 127 | 128 | // no intersection 129 | void Test3() 130 | { 131 | int numbers1[] = {1, 3, 5, 7}; 132 | vector array1(numbers1, numbers1 + sizeof(numbers1) / sizeof(int)); 133 | 134 | int numbers2[] = {2, 4, 6, 8}; 135 | vector array2(numbers2, numbers2 + sizeof(numbers2) / sizeof(int)); 136 | 137 | vector expected; 138 | 139 | Test("Test3", array1, array2, expected); 140 | } 141 | 142 | // one array only has one element 143 | void Test4() 144 | { 145 | int numbers1[] = {-2, 1, 4, 7}; 146 | vector array1(numbers1, numbers1 + sizeof(numbers1) / sizeof(int)); 147 | 148 | vector array2; 149 | array2.push_back(1); 150 | 151 | vector expected; 152 | expected.push_back(1); 153 | 154 | Test("Test4", array1, array2, expected); 155 | } 156 | 157 | // one array is empty 158 | void Test5() 159 | { 160 | int numbers1[] = {-2, 1, 4, 7}; 161 | vector array1(numbers1, numbers1 + sizeof(numbers1) / sizeof(int)); 162 | 163 | vector array2; 164 | 165 | vector expected; 166 | 167 | Test("Test5", array1, array2, expected); 168 | } 169 | 170 | int main(int argc, char* argv[]) 171 | { 172 | Test1(); 173 | Test2(); 174 | Test3(); 175 | Test4(); 176 | Test5(); 177 | 178 | return 0; 179 | } 180 | --------------------------------------------------------------------------------