├── c01_code ├── 01_HelloWorld │ └── helloworld.cpp ├── 02_Namespaces │ ├── namespaces.cpp │ ├── namespaces.h │ └── usingnamespaces.cpp ├── 03_HelloVariables │ └── hellovariables.cpp ├── 04_TypeTest │ └── typetest.cpp ├── 05_StronglyTypedEnums │ └── StronglyTypedEnums.cpp ├── 06_StructTest │ ├── employeestruct.h │ └── structtest.cpp ├── 07_std_array │ └── std_array.cpp ├── 08_std_vector │ └── vectortest.cpp ├── 09_InitializerLists │ └── InitializerLists.cpp ├── 10_StringTest │ └── stringtest.cpp ├── 11_NullPointerConstant │ └── NullPointerConstant.cpp ├── 12_SmartPointers │ └── SmartPointers.cpp ├── 13_ConstPointerArg │ └── ConstPointerArg.cpp ├── 14_ConstReferenceArg │ └── ConstReferenceArg.cpp ├── 15_Exceptions │ └── Exceptions.cpp ├── 16_AirlineTicket │ ├── AirlineTicket.cpp │ ├── AirlineTicket.h │ └── AirlineTicketTest.cpp ├── 17_UniformInitialization │ └── UniformInitialization.cpp └── 18_EmployeeDB │ ├── Database.cpp │ ├── Database.h │ ├── DatabaseTest.cpp │ ├── Employee.cpp │ ├── Employee.h │ ├── EmployeeTest.cpp │ └── UserInterface.cpp ├── c02_code ├── 01_CStrings │ ├── 01_strcpy.cpp │ ├── 02_strlen.cpp │ └── README.txt ├── 02_RawStringLiteral │ └── RawStringLiteral.cpp ├── 03_CppStrings │ └── CppStrings.cpp ├── 04_stoi │ └── stoi.cpp └── 05_StringViews │ └── StringViews.cpp ├── c07_code ├── 01_ArrayDelete │ └── ArrayDelete.cpp ├── 02_tictactoe │ └── tictactoe.cpp ├── 03_CharacterBoard │ └── CharacterBoard.cpp ├── 04_ArraysAndPointers │ └── ArraysAndPointers.cpp ├── 05_unique_ptr │ ├── 01_unique_ptr_move.cpp │ ├── 02_unique_ptr_malloc_int.cpp │ └── README.txt ├── 06_shared_ptr │ ├── 01_shared_ptr_malloc_int.cpp │ ├── 02_shared_ptr_file.cpp │ ├── 03_shared_ptr_double_delete.cpp │ ├── 04_shared_ptr_aliasing.cpp │ └── README.txt ├── 07_weak_ptr │ └── weak_ptr.cpp ├── 08_SmartPointersAndMoveSemantics │ └── unique_ptr_return_from_function.cpp ├── 09_enable_shared_from_this │ └── enable_shared_from_this.cpp └── 10_Leaky │ ├── Leaky MS VC++.cpp │ ├── Leaky.cpp │ └── README.txt ├── c08_code ├── 01_SpreadsheetCellNumOnly │ ├── AccessControl │ │ └── SpreadsheetCell.h │ ├── DeclarationOrder │ │ └── SpreadsheetCell.h │ ├── README.txt │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 02_SpreadsheetCellNumText │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 03_SpreadsheetCellThisAmbiguous │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 04_SpreadsheetCellThisUnambiguous │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 05_SpreadsheetCellNumTextHeap │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellHeap.cpp ├── 06_SpreadsheetCellNumTextHeapAlternate │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellHeapAlternate.cpp ├── 07_SpreadsheetCellNumTextSmartPointer │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellHeapSmartPointer.cpp ├── 08_SpreadsheetCellCtors │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 09_SpreadsheetCellArrayNoDefaultCtor │ ├── README.txt │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellArrayNoDefault.cpp ├── 10_SpreadsheetCellDefaultCtor │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 11_SpreadsheetCellExplicitlyDefaulted │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 12_SpreadsheetCellCtorInitializer │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 13_CtorInitializerOrder │ └── CtorInitializerOrder.cpp ├── 14_SpreadsheetCellCopyCtor │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 15_InitializerListCtor │ └── InitializerListCtor.cpp ├── 16_Destructors │ ├── DestructorExamples.cpp │ ├── DestructorHeapExamples.cpp │ ├── README.txt │ ├── SpreadsheetCell.cpp │ └── SpreadsheetCell.h ├── 17_SpreadsheetCellAssign │ ├── README.txt │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ ├── SpreadsheetCellAssignCopy.cpp │ └── SpreadsheetCellTest.cpp └── README.txt ├── c09_code ├── 01_Spreadsheet │ ├── Spreadsheet.cpp │ ├── Spreadsheet.h │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetTest.cpp ├── 02_SpreadsheetNoCopyAssign │ ├── README.txt │ ├── Spreadsheet.cpp │ ├── Spreadsheet.h │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetTest.cpp ├── 03_RvalueReferences │ └── RvalueReferences.cpp ├── 04_SpreadsheetMoveSemantics │ ├── Spreadsheet.cpp │ ├── Spreadsheet.h │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetTest.cpp ├── 05_SpreadsheetMoveSemanticsWithSwap │ ├── Spreadsheet.cpp │ ├── Spreadsheet.h │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetTest.cpp ├── 06_SpreadsheetCellMethods │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 07_SpreadsheetConstGetCellAt │ ├── Spreadsheet.cpp │ ├── Spreadsheet.h │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetTest.cpp ├── 08_SpreadsheetDefaultArguments │ ├── Spreadsheet.cpp │ ├── Spreadsheet.h │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetTest.cpp ├── 09_SpreadsheetDataMembers │ ├── Spreadsheet.cpp │ ├── Spreadsheet.h │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetTest.cpp ├── 10_NestedClasses │ ├── Spreadsheet.cpp │ ├── Spreadsheet.h │ └── SpreadsheetTest.cpp ├── 11_SpreadsheetCellColors │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 12_OperatorOverloading │ ├── AddFirstAttempt │ │ ├── SpreadsheetCell.cpp │ │ ├── SpreadsheetCell.h │ │ └── SpreadsheetCellTest.cpp │ ├── AddSecondAttempt │ │ ├── SpreadsheetCell.cpp │ │ ├── SpreadsheetCell.h │ │ └── SpreadsheetCellTest.cpp │ └── GlobalOperators │ │ ├── SpreadsheetCell.cpp │ │ ├── SpreadsheetCell.h │ │ └── SpreadsheetCellTest.cpp ├── 13_SeparateImpl │ ├── Spreadsheet.cpp │ ├── Spreadsheet.h │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ ├── SpreadsheetImpl.cpp │ ├── SpreadsheetImpl.h │ └── SpreadsheetTest.cpp └── README.txt ├── c10_code ├── 01_WeatherPrediction │ ├── MyWeatherPrediction.cpp │ ├── MyWeatherPrediction.h │ ├── WeatherPrediction.cpp │ └── WeatherPrediction.h ├── 02_ConstructorChain │ └── ConstructorChain.cpp ├── 03_Book │ └── Book.cpp ├── 04_PolymorphicSpreadsheet │ ├── DoubleSpreadsheetCell.cpp │ ├── DoubleSpreadsheetCell.h │ ├── SpreadsheetCell.h │ ├── SpreadsheetTest.cpp │ ├── StringSpreadsheetCell.cpp │ └── StringSpreadsheetCell.h ├── 05_DogBird │ ├── 01_DogBird.cpp │ ├── 02_Diamond.cpp │ └── README.txt ├── 06_Cherry │ ├── BingCherry.cpp │ ├── BingCherry.h │ ├── BingCherryTree.cpp │ ├── BingCherryTree.h │ ├── Cherry.cpp │ ├── Cherry.h │ ├── CherryTree.cpp │ ├── CherryTree.h │ └── TestCherry.cpp └── 07_MilesEstimator │ ├── EfficientCarMilesEstimator.cpp │ ├── EfficientCarMilesEstimator.h │ ├── MilesEstimator.cpp │ ├── MilesEstimator.h │ └── TestMilesEstimator.cpp ├── c11_code ├── 01_References │ ├── 01_ReferenceVariables.cpp │ ├── 02_ReferenceDataMembers.cpp │ ├── 03_ReferenceParameters.cpp │ ├── 04_OddsEvensPtrs.cpp │ ├── 05_OddsEvensRefs.cpp │ ├── 06_OddsEvensVector.cpp │ ├── 07_OddsEvensPairOfVector.cpp │ └── README.txt ├── 02_Const │ └── Const.cpp ├── 03_Constexpr │ ├── 01_constexpr.cpp │ ├── 02_constexprClasses.cpp │ └── README.txt ├── 04_Static │ ├── AnotherFile.cpp │ ├── FirstFile.cpp │ └── README.txt ├── 05_AnonymousNamespaces │ ├── AnotherFile.cpp │ ├── FirstFile.cpp │ └── README.txt ├── 06_Extern │ ├── AnotherFile.cpp │ ├── FirstFile.cpp │ └── README.txt ├── 07_StaticsInFunctions │ └── StaticsInFunctions.cpp ├── 08_Order │ └── order.cpp ├── 09_TypeAliases │ └── TypeAliases.cpp ├── 10_FunctionPointers │ └── FunctionPointers.cpp ├── 11_PtrsToMethodsAndMembers │ ├── Employee.cpp │ ├── Employee.h │ └── PtrsToMethodsAndMembers.cpp ├── 12_Casts │ ├── 01_ConstCast.cpp │ ├── 02_StaticCast.cpp │ ├── 03_ReinterpretCast.cpp │ ├── 04_DynamicCast.cpp │ └── README.txt ├── 13_Scope │ └── Scope.cpp ├── 14_noreturn │ └── noreturn.cpp ├── 15_UserDefinedLiterals │ └── UserDefinedLiterals.cpp ├── 16_VarArgs │ ├── 01_PrintfDemo.cpp │ ├── 02_VarArgs.cpp │ └── README.txt └── 17_Macros │ └── Square.cpp ├── c12_code ├── 01_GameBoard │ ├── GameBoard.cpp │ ├── GameBoard.h │ └── GameBoardTest.cpp ├── 02_Grid │ ├── 01_MethodsInHeader │ │ ├── Grid.h │ │ ├── GridTest.cpp │ │ ├── SpreadsheetCell.cpp │ │ └── SpreadsheetCell.h │ ├── 02_MethodsInSeparateHeader │ │ ├── Grid.h │ │ ├── GridDefinitions.h │ │ ├── GridTest.cpp │ │ ├── SpreadsheetCell.cpp │ │ └── SpreadsheetCell.h │ ├── 03_MethodsInSource │ │ ├── Grid.cpp │ │ ├── Grid.h │ │ ├── GridTest.cpp │ │ ├── README.txt │ │ ├── SpreadsheetCell.cpp │ │ └── SpreadsheetCell.h │ └── 04_ExplicitInstantiations │ │ ├── Grid.cpp │ │ ├── Grid.h │ │ └── GridTest.cpp ├── 03_GridNonType │ ├── Grid.h │ └── GridTest.cpp ├── 04_GridNonTypeDefault │ ├── Grid.h │ └── GridTest.cpp ├── 05_MethodTemplates │ ├── Grid.h │ └── GridTest.cpp ├── 06_MethodTemplatesNonType │ ├── Grid.h │ └── GridTest.cpp ├── 07_GridSpecialization │ ├── Grid.h │ ├── GridString.h │ └── GridTest.cpp ├── 08_GridInheritance │ ├── GameBoard.h │ ├── GameBoardTest.cpp │ └── Grid.h ├── 09_FunctionTemplate │ ├── 01_FindTemplate.cpp │ ├── 02_FindTemplateSpecialization.cpp │ ├── 03_FindTemplateOverload.cpp │ ├── 04_FindTemplateSpecialOverload.cpp │ ├── README.txt │ ├── SpreadsheetCell.cpp │ └── SpreadsheetCell.h ├── 10_FriendFunctionTemplates │ ├── Grid.h │ └── GridTest.cpp ├── 11_FunctionReturnType │ └── FunctionReturnType.cpp └── 12_decltype_auto │ └── decltype_auto.cpp ├── c13_code ├── 01_OutputBasics │ └── OutputBasics.cpp ├── 02_Write │ └── Write.cpp ├── 03_Put │ └── Put.cpp ├── 04_Flush │ └── flush.cpp ├── 05_Exceptions │ └── Exceptions.cpp ├── 06_Manipulator │ └── Manipulator.cpp ├── 07_Input │ ├── 01_string.cpp │ ├── 02_int.cpp │ ├── 03_getReservationData.cpp │ └── README.txt ├── 08_ErrorCheck │ └── ErrorCheck.cpp ├── 09_Get │ └── Get.cpp ├── 10_Unget │ └── Unget.cpp ├── 11_Peek │ └── Peek.cpp ├── 12_Getline │ └── Getline.cpp ├── 13_Muffin │ └── Muffin.cpp ├── 14_StringStream │ └── StringStream.cpp ├── 15_FileStream │ └── FileStream.cpp ├── 16_Seeking │ └── seeking.cpp ├── 17_tie │ └── tie.cpp └── 18_Bidirectional │ ├── Bidirectional.cpp │ └── data.txt ├── c14_code ├── 01_ReadIntegerFile │ ├── 01_NoExceptionHandling.cpp │ ├── 02_SafeDivide.cpp │ ├── 03_BasicExceptions.cpp │ ├── 04_ThrowInt.cpp │ ├── 05_ThrowCharStar.cpp │ ├── 06_CatchByValue.cpp │ ├── 07_CatchByNonConstReference.cpp │ ├── 08_ThrowingMultipleBasic.cpp │ ├── 09_ThrowingTwoTypes.cpp │ ├── 10_MatchingAnyException.cpp │ ├── 11_TerminateHandler.cpp │ ├── 12_noexcept.cpp │ ├── IntegerFile.txt │ └── README.txt ├── 02_ExceptionsAndPolymorphism │ ├── 01_UsingWhat.cpp │ ├── 02_CatchingPolymorphicallyCorrectOne.cpp │ ├── 03_CatchingPolymorphicallyCorrectTwo.cpp │ ├── 04_CatchingPolymorphicallyIncorrect.cpp │ ├── 05_WritingExceptions.cpp │ ├── IntegerFile.txt │ └── README.txt ├── 03_NestedException │ └── NestedException.cpp ├── 04_Rethrow │ ├── 01_rethrow.cpp │ ├── 02_rethrow.cpp │ └── README.txt ├── 05_StackUnwinding │ ├── 01_BadCode.cpp │ ├── 02_SmartPointer.cpp │ ├── 03_CatchAndRethrow.cpp │ └── README.txt ├── 06_NewFailures │ ├── 01_Exceptions.cpp │ ├── 02_Nothrow.cpp │ ├── 03_NewHandler.cpp │ └── README.txt ├── 07_ConstructorError │ ├── ConstructorErrorTest.cpp │ ├── Element.h │ └── Matrix.h ├── 08_FunctionTryBlock │ └── FunctionTryBlocks.cpp └── 09_GameBoard │ ├── GameBoard.cpp │ ├── GameBoard.h │ ├── GameBoardTest.cpp │ └── NoExceptions │ ├── GameBoard.cpp │ ├── GameBoard.h │ └── GameBoardTest.cpp ├── c15_code ├── 01_RelOps │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 02_ArithmeticOperators │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 03_StreamOperators │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 04_SubscriptOperator │ ├── Array.h │ └── ArrayTest.cpp ├── 05_AssociativeArray │ ├── AssociativeArray.h │ └── AssociativeArrayTest.cpp ├── 06_Functors │ └── Functors.cpp ├── 07_DereferenceOps │ ├── Pointer.h │ ├── PointerTest.cpp │ ├── SpreadsheetCell.cpp │ └── SpreadsheetCell.h ├── 08_ConversionsSpreadsheetCell │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 09_ExplicitConversionsSpreadsheetCell │ ├── SpreadsheetCell.cpp │ ├── SpreadsheetCell.h │ └── SpreadsheetCellTest.cpp ├── 10_ConversionsPointer │ ├── Pointer.h │ ├── PointerTest.cpp │ ├── SpreadsheetCell.cpp │ └── SpreadsheetCell.h ├── 11_ConversionsPointerBool │ ├── PointerBool.h │ ├── PointerBoolTest.cpp │ ├── SpreadsheetCell.cpp │ └── SpreadsheetCell.h ├── 12_Memory │ ├── MemoryDemo.cpp │ ├── MemoryDemo.h │ └── MemoryDemoTest.cpp └── 13_ExplicitDelete │ └── ExplicitDelete.cpp ├── c16_code └── 01_numeric_limits │ └── numeric_limits.cpp ├── c17_code ├── 01_TestScores │ ├── 01_TestScores.cpp │ ├── 02_TestScoresDynamic.cpp │ └── README.txt ├── 02_VectorCtors │ ├── 01_DefaultCtor.cpp │ ├── 02_InitialElements.cpp │ ├── 03_BuiltInClasses.cpp │ ├── 04_UserDefinedClasses.cpp │ ├── 05_InitializerList.cpp │ ├── 06_UniformInitialization.cpp │ ├── 07_HeapVectorsSmartPointer.cpp │ └── README.txt ├── 03_VectorCopyAssign │ └── demo.cpp ├── 04_VectorCompare │ └── compare.cpp ├── 05_VectorIterators │ ├── 01_TestScoresIterator.cpp │ ├── 02_AccessingFields.cpp │ ├── 03_ConstIterator.cpp │ ├── 04_IteratorSafety.cpp │ ├── 05_IteratorOps.cpp │ └── README.txt ├── 06_VectorOfReferences │ └── VectorOfReferences.cpp ├── 07_VectorAddRemove │ └── AddRemove.cpp ├── 08_CreateVectorOfSize │ └── CreateVectorOfSize.cpp ├── 09_MovePushBack │ └── MovePushBack.cpp ├── 10_Emplace │ └── Emplace.cpp ├── 11_RoundRobin │ ├── RoundRobin.h │ └── RoundRobinTest.cpp ├── 12_ListSplice │ └── ListSplice.cpp ├── 13_StudentEnrollment │ ├── Enrollment.cpp │ ├── course1.txt │ ├── course2.txt │ ├── course3.txt │ └── dropped.txt ├── 14_ForwardList │ └── forward_list.cpp ├── 15_std_array │ ├── 01_std_array.cpp │ ├── 02_get.cpp │ └── README.txt ├── 16_PacketBuffer │ ├── PacketBuffer.h │ └── PacketBufferTest.cpp ├── 17_ErrorCorrelatorPqueue │ ├── ErrorCorrelator.cpp │ ├── ErrorCorrelator.h │ └── ErrorCorrelatorTest.cpp ├── 18_ErrorCorrelatorStack │ ├── ErrorCorrelator.cpp │ ├── ErrorCorrelator.h │ └── ErrorCorrelatorTest.cpp ├── 19_Pair │ ├── PairTest.cpp │ └── README.txt ├── 20_MapBasics │ ├── 01_Map.cpp │ ├── 02_MapUniformInit.cpp │ ├── 03_MapInsert.cpp │ ├── 04_MapIndexOperator.cpp │ ├── 05_MapAsParameter.cpp │ ├── 06_MapIterators.cpp │ ├── 07_MapLookup.cpp │ ├── 08_MapFind.cpp │ ├── 09_MapErase.cpp │ └── README.txt ├── 21_Nodes │ ├── 01_ExtractAndInsert.cpp │ ├── 02_merge.cpp │ └── README.txt ├── 22_BankAccount │ ├── BankDB.cpp │ ├── BankDB.h │ └── BankDBTest.cpp ├── 23_BuddyList │ ├── BuddyList.cpp │ ├── BuddyList.h │ └── BuddyListTest.cpp ├── 24_AccessControlList │ ├── AccessList.cpp │ ├── AccessList.h │ └── AccessListTest.cpp ├── 25_CustomHash │ └── CustomHash.cpp ├── 26_unordered_map │ └── unordered_map.cpp ├── 27_PhoneBook │ └── PhoneBook.cpp ├── 28_ArrayIterators │ └── ArrayIterators.cpp ├── 29_StringContainers │ └── StringExample.cpp ├── 30_BitsetBasics │ ├── 01_BitsetBasics.cpp │ ├── 02_BitwiseOperators.cpp │ └── README.txt └── 31_CableCompany │ ├── CableCompany.cpp │ ├── CableCompany.h │ └── CableCompanyTest.cpp ├── c18_code ├── 01_AlgorithmOverview │ ├── 01_Find.cpp │ ├── 02_FindIf.cpp │ ├── 03_FindIfLambda.cpp │ ├── 04_Accumulate.cpp │ └── README.txt ├── 02_Function │ ├── 01_function.cpp │ ├── 02_function_find_if.cpp │ ├── 03_function_callback.cpp │ └── README.txt ├── 03_Lambdas │ ├── 01_LambdaBasic.cpp │ ├── 02_FindIfGenericLambda.cpp │ ├── 03_GenericCapture.cpp │ ├── 04_multiplyBy2Lambda.cpp │ ├── 05_count_if.cpp │ ├── 06_count_if_ref.cpp │ ├── 07_generate.cpp │ └── README.txt ├── 04_FunctionObjects │ ├── 01_Arithmetic.cpp │ ├── 02_QueueLess.cpp │ ├── 03_QueueGreater.cpp │ ├── 04_LogicalFunctors.cpp │ ├── 05_bind.cpp │ ├── 06_Ref.cpp │ ├── 07_BindWithOverloads.cpp │ ├── 08_BindWithFindIf.cpp │ ├── 09_Negators.cpp │ ├── 10_EmptyString.cpp │ ├── 11_EmptyStringPtr.cpp │ ├── 12_Invokers.cpp │ ├── 13_WritingFunctionObject.cpp │ ├── 14_WritingFunctionObjectLocal.cpp │ └── README.txt ├── 05_NonModifyingAlgorithms │ ├── 01_SearchAlgorithms.cpp │ ├── 02_BoyerMoore.cpp │ ├── 03_ComparisonAlgorithms.cpp │ ├── 04_CountingAlgorithms.cpp │ └── README.txt ├── 06_ModifyingAlgorithms │ ├── 01_TransformLambda.cpp │ ├── 02_TransformLambdaBinary.cpp │ ├── 03_copy.cpp │ ├── 04_copy_backward.cpp │ ├── 05_copy_if.cpp │ ├── 06_copy_n.cpp │ ├── 07_move.cpp │ ├── 08_replace.cpp │ ├── 09_remove.cpp │ ├── 10_sample.cpp │ └── README.txt ├── 07_OperationalAlgorithms │ ├── 01_ForEachBasicLambda.cpp │ ├── 02_SumAndProductLambda.cpp │ ├── 03_SumAndProduct.cpp │ ├── 04_ForEachN.cpp │ └── README.txt ├── 08_SwapAndExchangeAlgorithms │ ├── 01_swap.cpp │ ├── 02_exchange.cpp │ └── README.txt ├── 09_PartitionAlgorithms │ ├── 01_partition_copy.cpp │ ├── 02_partition.cpp │ └── README.txt ├── 10_SortingAlgorithms │ └── Sorting.cpp ├── 11_BinarySearchAlgorithms │ ├── 01_lower_bound.cpp │ ├── 02_binary_search.cpp │ └── README.txt ├── 12_SetAlgorithms │ ├── 01_Sets.cpp │ ├── 02_merge.cpp │ └── README.txt ├── 13_MinMaxAlgorithms │ ├── 01_min_max.cpp │ ├── 02_clamp.cpp │ └── README.txt ├── 14_ParallelAlgorithms │ └── ParallelSort.cpp ├── 15_NumericalAlgorithms │ ├── 01_inner_product.cpp │ ├── 02_iota.cpp │ ├── 03_reduce.cpp │ └── README.txt └── 16_AuditVoterRolls │ └── AuditVoterRolls.cpp ├── c19_code ├── 01_WideStrings │ └── wcout.cpp ├── 02_CharTypes │ └── CharTypes.cpp ├── 03_Imbue │ └── Imbue.cpp ├── 04_Locales │ └── Locales.cpp ├── 05_Facets │ └── use_facet.cpp └── 06_RegularExpressions │ ├── 01_regex_match_dates_1.cpp │ ├── 02_regex_match_dates_2.cpp │ ├── 03_regex_search_comments.cpp │ ├── 04_regex_iterator.cpp │ ├── 05_regex_token_iterator_1.cpp │ ├── 06_regex_token_iterator_2.cpp │ ├── 07_regex_token_iterator_field_splitting.cpp │ ├── 08_regex_replace_1.cpp │ ├── 08_regex_replace_2.cpp │ ├── 10_regex_replace_3.cpp │ └── README.txt ├── c20_code ├── 01_Ratio │ └── ratios.cpp ├── 02_Chrono │ ├── 01_durations.cpp │ ├── 02_now_put_time.cpp │ ├── 03_now.cpp │ ├── 04_timing.cpp │ ├── 05_time_point.cpp │ ├── 06_time_point_conversions.cpp │ └── README.txt ├── 03_Random │ ├── 01_old.cpp │ ├── 02_random_device.cpp │ ├── 03_basic.cpp │ ├── 04_generate.cpp │ ├── 05_generate_function.cpp │ ├── 06_uniform_int_distribution.cpp │ ├── 07_normal_distribution.cpp │ └── README.txt ├── 04_optional │ └── optional.cpp ├── 05_variant │ └── variant.cpp ├── 06_any │ └── any.cpp ├── 07_Tuple │ ├── 01_pair.cpp │ ├── 02_tuple.cpp │ ├── 03_structured_bindings.cpp │ ├── 04_tuple_tie.cpp │ ├── 05_tuple_cat.cpp │ ├── 06_tuple_comparison.cpp │ ├── 07_operator_less_than.cpp │ ├── 08_make_from_tuple.cpp │ ├── 09_apply.cpp │ └── README.txt └── 08_Filesystem │ ├── 01_paths.cpp │ ├── 02_path_append.cpp │ ├── 03_path_concat.cpp │ ├── 04_path_component_iterator.cpp │ ├── 05_directory_entry.cpp │ ├── 06_space_info.cpp │ ├── 07_recursive_directory_iterator.cpp │ ├── 08_directory_iterator.cpp │ └── README.txt ├── c21_code ├── 01_StreamIterators │ ├── 01_OutputStreamIterators.cpp │ ├── 02_InputStreamIterators.cpp │ └── README.txt ├── 02_IteratorAdaptors │ ├── 01_ReverseIterators.cpp │ ├── 02_BackInsertIterator.cpp │ ├── 03_InsertIterator.cpp │ ├── 04_MoveIterators.cpp │ └── README.txt ├── 03_WritingAlgorithms │ ├── 01_FindAll.cpp │ ├── 02_IteratorTraitsTest.cpp │ └── README.txt ├── 04_BasicHashmap │ ├── hash_map.h │ ├── hash_map.inl │ └── test_hash_map.cpp └── 05_FinalHashmap │ ├── hash_map.h │ ├── hash_map.inl │ └── test_hash_map.cpp ├── c22_code ├── 01_GridTemplateContainer │ ├── Grid.h │ └── GridTest.cpp ├── 02_GridTemplateContainerDefault │ ├── GridDefault.h │ └── GridDefaultTest.cpp ├── 03_GridTemplateContainerTemplateTemplate │ ├── GridTemplateTemplate.h │ └── GridTemplateTemplateTest.cpp ├── 04_GridDefaultElementValue │ ├── Grid.h │ ├── GridTest.cpp │ ├── SpreadsheetCell.cpp │ └── SpreadsheetCell.h ├── 05_GridDefaultElementValueRef │ ├── GridRefNonType.h │ ├── GridTestRefNonType.cpp │ ├── SpreadsheetCell.cpp │ └── SpreadsheetCell.h ├── 06_GridPartialString │ ├── Grid.h │ ├── GridString.h │ ├── GridTest.cpp │ ├── GridTestString.cpp │ └── README.txt ├── 07_GridPartialPtr │ ├── Grid.h │ ├── GridPtr.h │ └── GridPtrTest.cpp ├── 08_FunctionTemplatePtr │ ├── FindTemplatePtr.cpp │ ├── SpreadsheetCell.cpp │ └── SpreadsheetCell.h ├── 09_OneDGrid │ ├── OneDGrid.h │ └── OneDGridTest.cpp ├── 10_NDGrid │ ├── NDGrid.h │ └── NDGridTest.cpp ├── 11_VarArgs │ └── VarArgsWithVariadicTemplates.cpp ├── 12_VariadicMixins │ └── VariadicMixins.cpp ├── 13_Folding │ ├── 01_processValues.cpp │ ├── 02_printValues.cpp │ ├── 03_sumValues.cpp │ └── README.txt ├── 14_Factorial │ ├── 01_Factorial.cpp │ ├── 02_constexpr.cpp │ └── README.txt ├── 15_LoopUnrolling │ └── LoopUnrolling.cpp ├── 16_PrintTuple │ ├── 01_PrintTuple.cpp │ ├── 02_PrintTupleSimplified.cpp │ ├── 03_constexpr_if.cpp │ ├── 04_constexpr_if_function.cpp │ ├── 05_constexpr_if_simplified.cpp │ ├── 06_index_sequence.cpp │ └── README.txt └── 17_TypeTraits │ ├── 01_basic.cpp │ ├── 02_is_integral.cpp │ ├── 03_is_integral_constexpr_if.cpp │ ├── 04_is_same.cpp │ ├── 05_enable_if.cpp │ ├── 06_doit_enable_if.cpp │ ├── 07_doit_constexpr_if.cpp │ ├── 08_doit_constexpr_if_is_invocable.cpp │ ├── 09_logical_operator_traits.cpp │ └── README.txt ├── c23_code ├── 01_thread │ ├── 01_ThreadFunction.cpp │ ├── 02_ThreadFunctionObject.cpp │ ├── 03_ThreadLambda.cpp │ ├── 04_ThreadMemFunc.cpp │ └── README.txt ├── 02_ExceptionsWithThreads │ └── ExceptionsWithThreads.cpp ├── 03_atomic │ ├── 01_is_lock_free.cpp │ ├── 02_inc_func_non_atomic.cpp │ ├── 03_inc_func_atomic.cpp │ ├── 04_inc_func_atomic_optimal.cpp │ ├── 05_fetch_add.cpp │ └── README.txt ├── 04_mutex │ ├── 01_multiple_locks.cpp │ ├── 02_scoped_lock.cpp │ ├── 03_call_once.cpp │ ├── 04_ThreadFunctionObjectWithMutex.cpp │ ├── 05_ThreadFunctionObjectWithTimedMutex.cpp │ ├── 06_double_checked_locking.cpp │ └── README.txt ├── 05_future │ ├── 01_promise_future.cpp │ ├── 02_packaged_task.cpp │ ├── 03_async.cpp │ ├── 04_async_error_handling.cpp │ ├── 05_shared_future.cpp │ └── README.txt └── 06_logger │ ├── FinalVersion │ ├── Logger.cpp │ ├── Logger.h │ └── main.cpp │ └── Version1 │ ├── Logger.cpp │ ├── Logger.h │ └── main.cpp ├── c25_code ├── 01_Person │ └── Person.cpp ├── 02_ObjectPool │ ├── ObjectPool.h │ └── ObjectPoolTest.cpp └── 03_NameDB │ ├── FirstAttempt │ ├── NameDB.cpp │ ├── NameDB.h │ └── NameDBTest.cpp │ ├── SecondAttempt │ ├── NameDB.cpp │ ├── NameDB.h │ └── NameDBTest.cpp │ ├── ThirdAttempt │ ├── NameDB.cpp │ ├── NameDB.h │ └── NameDBTest.cpp │ └── boys_long.txt ├── c26_code └── ObjectPoolTest │ ├── ObjectPool.h │ ├── ObjectPoolTest.cpp │ ├── ObjectPoolTest.h │ ├── README.txt │ ├── Serial.cpp │ └── Serial.h ├── c27_code ├── 01_StartTimeDebugMode │ └── STDebug.cpp ├── 02_CompileTimeDebugMode │ └── CTDebug.cpp ├── 03_RingBuffer │ ├── RingBuffer.cpp │ ├── RingBuffer.h │ └── RingBufferTest.cpp ├── 04_StaticAssert │ └── StaticAssert.cpp ├── 05_MemoryErrors │ ├── MemoryErrors.cpp │ └── README.txt └── 06_ArticleCitations │ ├── 01_FirstAttempt │ ├── ArticleCitations.cpp │ └── ArticleCitations.h │ ├── 02_CoutDebugging │ ├── ArticleCitations.cpp │ └── ArticleCitations.h │ ├── 03_CoutDebuggingWithStreamState │ ├── ArticleCitations.cpp │ └── ArticleCitations.h │ ├── 04_AfterCoutDebugging │ ├── ArticleCitations.cpp │ └── ArticleCitations.h │ ├── 05_FinalVersion │ ├── ArticleCitations.cpp │ └── ArticleCitations.h │ ├── 06_VisualStudio │ ├── ArticleCitations.cpp │ ├── ArticleCitations.h │ └── ArticleCitationsTest.cpp │ ├── ArticleCitationsTest.cpp │ ├── README.txt │ ├── paper1.txt │ └── paper2.txt ├── c28_code ├── 01_Simple │ ├── DerivedSimple.cpp │ ├── DerivedSimple.h │ ├── Simple.cpp │ └── Simple.h ├── 02_CopyAndSwap │ ├── CopyAndSwap.cpp │ └── CopyAndSwap.h ├── 03_Exceptions │ └── Exceptions.cpp ├── 04_FileRead │ └── FileRead.cpp ├── 05_FileWrite │ └── FileWrite.cpp ├── 06_Template │ ├── SimpleTemplate.h │ └── TemplateTest.cpp ├── 07_RAII │ └── RAII.cpp └── 08_DoubleDispatch │ ├── 01_DoubleDispatchBruteForce.cpp │ ├── 02_DoubleDispatch.cpp │ └── README.txt ├── c29_code ├── 01_SingletonLogger │ ├── Logger.cpp │ ├── Logger.h │ └── TestSingletonLogger.cpp ├── 02_CarFactory │ ├── Car.h │ ├── CarFactory.cpp │ ├── CarFactory.h │ └── CarTest.cpp ├── 03_LoggerAdaptor │ ├── LoggerAdaptor.cpp │ ├── LoggerAdaptor.h │ └── TestLoggerAdaptor.cpp ├── 04_Decorator │ └── Decorator.cpp ├── 05_ChainOfResponsibility │ └── ChainOfResponsibility.cpp └── 06_Observer │ └── Observer.cpp └── c30_code ├── 01_PtrSize └── PtrSize.cpp ├── 02_VariableArray ├── README.txt └── VariableArray.cpp ├── 03_MixingC ├── MixingC.cpp └── README.txt ├── 04_CSharp ├── HelloCSharp.cs └── HelloCpp.cpp ├── 05_JNI ├── HelloCpp.cpp └── HelloCpp.java └── 06_Perl ├── README.txt ├── encryptString.cpp ├── processLog.pl └── userlog.txt /c01_code/01_HelloWorld/helloworld.cpp: -------------------------------------------------------------------------------- 1 | // helloworld.cpp 2 | 3 | #include 4 | 5 | int main() 6 | { 7 | std::cout << "Hello, World!" << std::endl; 8 | 9 | return 0; 10 | } 11 | -------------------------------------------------------------------------------- /c01_code/02_Namespaces/namespaces.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include "namespaces.h" 3 | 4 | //namespace mycode { 5 | // void foo() 6 | // { 7 | // std::cout << "foo() called in the mycode namespace" << std::endl; 8 | // } 9 | //} 10 | 11 | 12 | void mycode::foo() 13 | { 14 | std::cout << "foo() called in the mycode namespace" << std::endl; 15 | } 16 | -------------------------------------------------------------------------------- /c01_code/02_Namespaces/namespaces.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | namespace mycode { 4 | void foo(); 5 | } 6 | -------------------------------------------------------------------------------- /c01_code/02_Namespaces/usingnamespaces.cpp: -------------------------------------------------------------------------------- 1 | #include "namespaces.h" 2 | 3 | using namespace mycode; 4 | 5 | int main() 6 | { 7 | mycode::foo(); // Calls the "foo" function in the "mycode" namespace 8 | foo(); // implies mycode::foo(); 9 | return 0; 10 | } 11 | -------------------------------------------------------------------------------- /c01_code/03_HelloVariables/hellovariables.cpp: -------------------------------------------------------------------------------- 1 | // NOTE: Most compilers will issue a warning or an error 2 | // when code is using uninitialized variables. Some compilers 3 | // will generate code that will report an error at run time. 4 | 5 | #include 6 | 7 | using namespace std; 8 | 9 | int main() 10 | { 11 | int uninitializedInt; 12 | int initializedInt = 7; 13 | 14 | cout << uninitializedInt << " is a random value" << endl; 15 | cout << initializedInt << " was assigned an initial value" << endl; 16 | 17 | return 0; 18 | } 19 | -------------------------------------------------------------------------------- /c01_code/04_TypeTest/typetest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | int someInteger = 256; 8 | short someShort; 9 | long someLong; 10 | float someFloat; 11 | double someDouble; 12 | 13 | someInteger++; 14 | someInteger *= 2; 15 | someShort = static_cast(someInteger); 16 | someLong = someShort * 10000; 17 | someFloat = someLong + 0.785f; 18 | someDouble = static_cast(someFloat) / 100000; 19 | 20 | cout << someDouble << endl; 21 | 22 | return 0; 23 | } 24 | -------------------------------------------------------------------------------- /c01_code/05_StronglyTypedEnums/StronglyTypedEnums.cpp: -------------------------------------------------------------------------------- 1 | enum class PieceType 2 | { 3 | King = 1, 4 | Queen, 5 | Rook = 10, 6 | Pawn 7 | }; 8 | 9 | int main() 10 | { 11 | PieceType piece = PieceType::King; 12 | 13 | if (piece == PieceType::King) 14 | { 15 | /* ... */ 16 | } 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c01_code/06_StructTest/employeestruct.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | struct Employee { 4 | char firstInitial; 5 | char lastInitial; 6 | int employeeNumber; 7 | int salary; 8 | }; 9 | -------------------------------------------------------------------------------- /c01_code/06_StructTest/structtest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include "employeestruct.h" 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | // Create and populate an employee. 9 | Employee anEmployee; 10 | 11 | anEmployee.firstInitial = 'M'; 12 | anEmployee.lastInitial = 'G'; 13 | anEmployee.employeeNumber = 42; 14 | anEmployee.salary = 80000; 15 | 16 | // Output the values of an employee. 17 | cout << "Employee: " << anEmployee.firstInitial << 18 | anEmployee.lastInitial << endl; 19 | cout << "Number: " << anEmployee.employeeNumber << endl; 20 | cout << "Salary: $" << anEmployee.salary << endl; 21 | 22 | return 0; 23 | } 24 | -------------------------------------------------------------------------------- /c01_code/07_std_array/std_array.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | array arr = { 9, 8, 7 }; 9 | cout << "Array size = " << arr.size() << endl; 10 | cout << "2nd element = " << arr[1] << endl; 11 | 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c01_code/08_std_vector/vectortest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | // Create a vector of integers 9 | vector myVector = { 11, 22 }; 10 | 11 | // Add some more integers to the vector using push_back() 12 | myVector.push_back(33); 13 | myVector.push_back(44); 14 | 15 | // Access elements 16 | cout << "1st element: " << myVector[0] << endl; 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c01_code/09_InitializerLists/InitializerLists.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int makeSum(initializer_list lst) 7 | { 8 | int total = 0; 9 | for (int value : lst) { 10 | total += value; 11 | } 12 | return total; 13 | } 14 | 15 | int main() 16 | { 17 | int a = makeSum({ 1,2,3 }); 18 | int b = makeSum({ 10,20,30,40,50,60 }); 19 | 20 | cout << a << endl; 21 | cout << b << endl; 22 | 23 | cout << makeSum({ 1, 2, 3 }) << endl; 24 | 25 | return 0; 26 | } 27 | -------------------------------------------------------------------------------- /c01_code/10_StringTest/stringtest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | string myString = "Hello, World"; 9 | cout << "The value of myString is " << myString << endl; 10 | cout << "The second letter is " << myString[1] << endl; 11 | 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c01_code/11_NullPointerConstant/NullPointerConstant.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | void func(char* str) {cout << "char* version" << endl;} 6 | void func(int i) {cout << "int version" << endl;} 7 | 8 | int main() 9 | { 10 | func(NULL); 11 | func(nullptr); 12 | 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /c01_code/13_ConstPointerArg/ConstPointerArg.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | void mysteryFunction(const std::string* someString) 4 | { 5 | *someString = "Test"; // Will not compile. 6 | } 7 | 8 | int main() 9 | { 10 | std::string myString = "The string"; 11 | mysteryFunction(&myString); 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c01_code/14_ConstReferenceArg/ConstReferenceArg.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | void printString(const std::string& myString) 5 | { 6 | std::cout << myString << std::endl; 7 | } 8 | 9 | int main() 10 | { 11 | std::string someString = "Hello World"; 12 | printString(someString); 13 | printString("Hello World"); // Passing literals works 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c01_code/15_Exceptions/Exceptions.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | double divideNumbers(double numerator, double denominator) 7 | { 8 | if (denominator == 0) { 9 | throw invalid_argument("Denominator cannot be 0."); 10 | } 11 | return numerator / denominator; 12 | } 13 | 14 | int main() 15 | { 16 | try { 17 | cout << divideNumbers(2.5, 0.5) << endl; 18 | cout << divideNumbers(2.3, 0) << endl; 19 | cout << divideNumbers(4.5, 2.5) << endl; 20 | } catch (const invalid_argument& exception) { 21 | cout << "Exception caught: " << exception.what() << endl; 22 | } 23 | 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /c01_code/16_AirlineTicket/AirlineTicket.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | 5 | class AirlineTicket 6 | { 7 | public: 8 | AirlineTicket(); 9 | ~AirlineTicket(); 10 | 11 | double calculatePriceInDollars() const; 12 | 13 | const std::string& getPassengerName() const; 14 | void setPassengerName(const std::string& name); 15 | 16 | int getNumberOfMiles() const; 17 | void setNumberOfMiles(int miles); 18 | 19 | bool hasEliteSuperRewardsStatus() const; 20 | void setHasEliteSuperRewardsStatus(bool status); 21 | 22 | private: 23 | std::string mPassengerName; 24 | int mNumberOfMiles; 25 | bool mHasEliteSuperRewardsStatus; 26 | }; 27 | 28 | -------------------------------------------------------------------------------- /c01_code/18_EmployeeDB/EmployeeTest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include "Employee.h" 3 | 4 | using namespace std; 5 | using namespace Records; 6 | /* 7 | int main() 8 | { 9 | cout << "Testing the Employee class." << endl; 10 | 11 | Employee emp; 12 | emp.setFirstName("John"); 13 | emp.setLastName("Doe"); 14 | emp.setEmployeeNumber(71); 15 | emp.setSalary(50000); 16 | emp.promote(); 17 | emp.promote(50); 18 | emp.hire(); 19 | emp.display(); 20 | 21 | return 0; 22 | } 23 | */ -------------------------------------------------------------------------------- /c02_code/01_CStrings/02_strlen.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | char text1[] = "abcdef"; 10 | size_t s1 = sizeof(text1); // is 7 11 | size_t s2 = strlen(text1); // is 6 12 | cout << s1 << endl << s2 << endl; 13 | 14 | const char* text2 = "abcdef"; 15 | size_t s3 = sizeof(text2); // is platform-dependent (e.g. 4 bytes for x86, 8 bytes for x64) 16 | size_t s4 = strlen(text2); // is 6 17 | cout << s3 << endl << s4 << endl; 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c02_code/01_CStrings/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | 3 | -------------------------------------------------------------------------------- /c02_code/02_RawStringLiteral/RawStringLiteral.cpp: -------------------------------------------------------------------------------- 1 | int main() 2 | { 3 | //const char* str1 = "Hello "World"!"; // Error! 4 | const char* str2 = "Hello \"World\"!"; 5 | const char* str3 = R"(Hello "World"!)"; 6 | 7 | const char* str4 = "Line 1\nLine 2"; 8 | const char* str5 = R"(Line 1 9 | Line 2)"; 10 | 11 | const char* str6 = R"(Is the following a tab character? \t)"; 12 | 13 | //const char* str7 = R"(Embedded )" characters)"; // Error! 14 | const char* str8 = R"-(Embedded )" characters)-"; 15 | 16 | return 0; 17 | } 18 | -------------------------------------------------------------------------------- /c02_code/03_CppStrings/CppStrings.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | string myString = "hello"; 9 | 10 | myString += ", there"; 11 | 12 | string myOtherString = myString; 13 | 14 | if (myString == myOtherString) { 15 | myOtherString[0] = 'H'; 16 | } 17 | 18 | cout << myString << endl; 19 | cout << myOtherString << endl; 20 | 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /c02_code/04_stoi/stoi.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | const string toParse = " 123USD"; 10 | size_t index = 0; 11 | int value = stoi(toParse, &index); 12 | cout << "Parsed value: " << value << endl; 13 | cout << "First non-parsed character: '" << toParse[index] << "'" << endl; 14 | 15 | return 0; 16 | } -------------------------------------------------------------------------------- /c07_code/02_tictactoe/tictactoe.cpp: -------------------------------------------------------------------------------- 1 | int main() 2 | { 3 | char board[3][3] = {}; 4 | // Test code 5 | board[0][0] = 'X'; // X puts marker in position (0,0). 6 | board[2][1] = 'O'; // O puts marker in position (2,1). 7 | 8 | return 0; 9 | } 10 | -------------------------------------------------------------------------------- /c07_code/05_unique_ptr/01_unique_ptr_move.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | class Foo 6 | { 7 | public: 8 | Foo(unique_ptr data) : mData(move(data)) { } 9 | 10 | private: 11 | unique_ptr mData; 12 | }; 13 | 14 | int main() 15 | { 16 | auto myIntSmartPtr = make_unique(42); 17 | Foo f(move(myIntSmartPtr)); 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c07_code/05_unique_ptr/02_unique_ptr_malloc_int.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int* malloc_int(int value) 7 | { 8 | int* p = (int*)malloc(sizeof(int)); 9 | *p = value; 10 | return p; 11 | } 12 | 13 | int main() 14 | { 15 | unique_ptr myIntSmartPtr(malloc_int(42), free); 16 | return 0; 17 | } 18 | -------------------------------------------------------------------------------- /c07_code/05_unique_ptr/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c07_code/06_shared_ptr/01_shared_ptr_malloc_int.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int* malloc_int(int value) 7 | { 8 | int* p = (int*)malloc(sizeof(int)); 9 | *p = value; 10 | return p; 11 | } 12 | 13 | int main() 14 | { 15 | shared_ptr myIntSmartPtr(malloc_int(42), free); 16 | 17 | return 0; 18 | } 19 | -------------------------------------------------------------------------------- /c07_code/06_shared_ptr/04_shared_ptr_aliasing.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | class Foo 6 | { 7 | public: 8 | Foo(int value) : mData(value) { } 9 | int mData; 10 | }; 11 | 12 | int main() 13 | { 14 | auto foo = make_shared(42); 15 | auto aliasing = shared_ptr(foo, &foo->mData); 16 | 17 | return 0; 18 | } -------------------------------------------------------------------------------- /c07_code/06_shared_ptr/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c07_code/08_SmartPointersAndMoveSemantics/unique_ptr_return_from_function.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | class Simple 7 | { 8 | public: 9 | Simple() { cout << "Simple constructor called!" << endl; } 10 | ~Simple() { cout << "Simple destructor called!" << endl; } 11 | }; 12 | 13 | unique_ptr create() 14 | { 15 | auto ptr = make_unique(); 16 | // Do something with ptr... 17 | return ptr; 18 | } 19 | 20 | int main() 21 | { 22 | unique_ptr mySmartPtr1 = create(); 23 | auto mySmartPtr2 = create(); 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /c07_code/09_enable_shared_from_this/enable_shared_from_this.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | class Foo : public enable_shared_from_this 6 | { 7 | public: 8 | shared_ptr getPointer() { 9 | return shared_from_this(); 10 | } 11 | }; 12 | 13 | int main() 14 | { 15 | auto ptr1 = make_shared(); 16 | auto ptr2 = ptr1->getPointer(); 17 | } 18 | -------------------------------------------------------------------------------- /c07_code/10_Leaky/Leaky.cpp: -------------------------------------------------------------------------------- 1 | class Simple 2 | { 3 | public: 4 | Simple() { mIntPtr = new int(); } 5 | ~Simple() { delete mIntPtr; } 6 | 7 | void setValue(int value) { *mIntPtr = value; } 8 | 9 | private: 10 | int* mIntPtr; 11 | }; 12 | 13 | void doSomething(Simple*& outSimplePtr) 14 | { 15 | outSimplePtr = new Simple(); // BUG! Doesn't delete the original. 16 | } 17 | 18 | int main() 19 | { 20 | Simple* simplePtr = new Simple(); // Allocate a Simple object. 21 | 22 | doSomething(simplePtr); 23 | 24 | delete simplePtr; // Only cleans up the second object. 25 | 26 | return 0; 27 | } 28 | -------------------------------------------------------------------------------- /c07_code/10_Leaky/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | 3 | "Leaky MS VC++.cpp" should be compiled with Microsoft Visual C++. 4 | "Leaky.cpp" can be compiled on any platform. 5 | -------------------------------------------------------------------------------- /c08_code/01_SpreadsheetCellNumOnly/AccessControl/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | class SpreadsheetCell 4 | { 5 | void setValue(double inValue); 6 | public: 7 | double getValue() const; 8 | 9 | private: 10 | double mValue; 11 | }; 12 | -------------------------------------------------------------------------------- /c08_code/01_SpreadsheetCellNumOnly/DeclarationOrder/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | class SpreadsheetCell 4 | { 5 | public: 6 | void setValue(double inValue); 7 | 8 | private: 9 | double mValue; 10 | 11 | public: 12 | double getValue() const; 13 | }; 14 | -------------------------------------------------------------------------------- /c08_code/01_SpreadsheetCellNumOnly/README.txt: -------------------------------------------------------------------------------- 1 | The subdirectories AccessControl and DeclarationOrder contain alternative 2 | versions of the SpreadsheetCell.h header file. You can test these alternative 3 | versions by modifying SpreadsheetCell.cpp and SpreadsheetCellTest.cpp to 4 | include the header file from these subdirectories instead of the one in 5 | this directory. 6 | 7 | Note that when you use the version in AccessControl, the code doesn't compile. 8 | 9 | -------------------------------------------------------------------------------- /c08_code/01_SpreadsheetCellNumOnly/SpreadsheetCell.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | 3 | void SpreadsheetCell::setValue(double inValue) 4 | { 5 | mValue = inValue; 6 | } 7 | 8 | double SpreadsheetCell::getValue() const 9 | { 10 | return mValue; 11 | } 12 | -------------------------------------------------------------------------------- /c08_code/01_SpreadsheetCellNumOnly/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | class SpreadsheetCell 4 | { 5 | public: 6 | void setValue(double inValue); 7 | double getValue() const; 8 | 9 | private: 10 | double mValue; 11 | }; 12 | -------------------------------------------------------------------------------- /c08_code/01_SpreadsheetCellNumOnly/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell cell1; 9 | cell1.setValue(5.3); 10 | cout << cell1.getValue() << endl; 11 | 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c08_code/02_SpreadsheetCellNumText/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | void setValue(double inValue); 10 | double getValue() const; 11 | 12 | void setString(std::string_view inString); 13 | std::string getString() const; 14 | 15 | private: 16 | std::string doubleToString(double inValue) const; 17 | double stringToDouble(std::string_view inString) const; 18 | 19 | double mValue; 20 | }; 21 | -------------------------------------------------------------------------------- /c08_code/02_SpreadsheetCellNumText/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell myCell, anotherCell; 9 | myCell.setValue(6); 10 | anotherCell.setString("3.2"); 11 | 12 | cout << "cell 1: " << myCell.getValue() << endl; 13 | cout << "cell 2: " << anotherCell.getValue() << endl; 14 | 15 | cout << "cell 1: " << myCell.getString() << endl; 16 | cout << "cell 2: " << anotherCell.getString() << endl; 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c08_code/03_SpreadsheetCellThisAmbiguous/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | void setValue(double value); 10 | double getValue() const; 11 | 12 | void setString(std::string_view inString); 13 | std::string getString() const; 14 | 15 | private: 16 | std::string doubleToString(double inValue) const; 17 | double stringToDouble(std::string_view inString) const; 18 | 19 | double value; 20 | }; 21 | -------------------------------------------------------------------------------- /c08_code/03_SpreadsheetCellThisAmbiguous/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell myCell, anotherCell; 9 | myCell.setValue(6); 10 | anotherCell.setString("3.2"); 11 | 12 | cout << "cell 1: " << myCell.getValue() << endl; 13 | cout << "cell 2: " << anotherCell.getValue() << endl; 14 | 15 | cout << "cell 1: " << myCell.getString() << endl; 16 | cout << "cell 2: " << anotherCell.getString() << endl; 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c08_code/04_SpreadsheetCellThisUnambiguous/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | void setValue(double value); 10 | double getValue() const; 11 | 12 | void setString(std::string_view inString); 13 | std::string getString() const; 14 | 15 | private: 16 | std::string doubleToString(double inValue) const; 17 | double stringToDouble(std::string_view inString) const; 18 | 19 | double value; 20 | }; 21 | -------------------------------------------------------------------------------- /c08_code/04_SpreadsheetCellThisUnambiguous/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell myCell, anotherCell; 9 | myCell.setValue(6); 10 | anotherCell.setString("3.2"); 11 | 12 | cout << "cell 1: " << myCell.getValue() << endl; 13 | cout << "cell 2: " << anotherCell.getValue() << endl; 14 | 15 | cout << "cell 1: " << myCell.getString() << endl; 16 | cout << "cell 2: " << anotherCell.getString() << endl; 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c08_code/05_SpreadsheetCellNumTextHeap/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | void setValue(double inValue); 10 | double getValue() const; 11 | 12 | void setString(std::string_view inString); 13 | std::string getString() const; 14 | 15 | private: 16 | std::string doubleToString(double inValue) const; 17 | double stringToDouble(std::string_view inString) const; 18 | 19 | double mValue; 20 | }; 21 | -------------------------------------------------------------------------------- /c08_code/05_SpreadsheetCellNumTextHeap/SpreadsheetCellHeap.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell* myCellp = new SpreadsheetCell(); 9 | 10 | myCellp->setValue(3.7); 11 | cout << "cell 1: " << myCellp->getValue() << 12 | " " << myCellp->getString() << endl; 13 | delete myCellp; 14 | myCellp = nullptr; 15 | 16 | return 0; 17 | } 18 | -------------------------------------------------------------------------------- /c08_code/06_SpreadsheetCellNumTextHeapAlternate/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | void setValue(double inValue); 10 | double getValue() const; 11 | 12 | void setString(std::string_view inString); 13 | std::string getString() const; 14 | 15 | private: 16 | std::string doubleToString(double inValue) const; 17 | double stringToDouble(std::string_view inString) const; 18 | 19 | double mValue; 20 | }; 21 | -------------------------------------------------------------------------------- /c08_code/06_SpreadsheetCellNumTextHeapAlternate/SpreadsheetCellHeapAlternate.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell* myCellp = new SpreadsheetCell(); 9 | 10 | (*myCellp).setValue(3.7); 11 | cout << "cell 1: " << (*myCellp).getValue() << 12 | " " << (*myCellp).getString() << endl; 13 | delete myCellp; 14 | myCellp = nullptr; 15 | 16 | return 0; 17 | } 18 | -------------------------------------------------------------------------------- /c08_code/07_SpreadsheetCellNumTextSmartPointer/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | void setValue(double inValue); 10 | double getValue() const; 11 | 12 | void setString(std::string_view inString); 13 | std::string getString() const; 14 | 15 | private: 16 | std::string doubleToString(double inValue) const; 17 | double stringToDouble(std::string_view inString) const; 18 | 19 | double mValue; 20 | }; 21 | -------------------------------------------------------------------------------- /c08_code/07_SpreadsheetCellNumTextSmartPointer/SpreadsheetCellHeapSmartPointer.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | auto myCellp = make_unique(); 10 | // Equivalent to: 11 | // unique_ptr myCellp(new SpreadsheetCell()); 12 | 13 | myCellp->setValue(3.7); 14 | cout << "cell 1: " << myCellp->getValue() << 15 | " " << myCellp->getString() << endl; 16 | 17 | return 0; 18 | } 19 | -------------------------------------------------------------------------------- /c08_code/08_SpreadsheetCellCtors/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell(double initialValue); 10 | SpreadsheetCell(std::string_view initialValue); 11 | 12 | void setValue(double inValue); 13 | double getValue() const; 14 | 15 | void setString(std::string_view inString); 16 | std::string getString() const; 17 | 18 | private: 19 | std::string doubleToString(double inValue) const; 20 | double stringToDouble(std::string_view inString) const; 21 | 22 | double mValue; 23 | }; 24 | -------------------------------------------------------------------------------- /c08_code/09_SpreadsheetCellArrayNoDefaultCtor/README.txt: -------------------------------------------------------------------------------- 1 | Note that SpreadsheetCellArrayNoDefault.cpp does not compile. 2 | 3 | 4 | -------------------------------------------------------------------------------- /c08_code/09_SpreadsheetCellArrayNoDefaultCtor/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell(double initialValue); 10 | SpreadsheetCell(std::string_view initialValue); 11 | 12 | void setValue(double inValue); 13 | double getValue() const; 14 | 15 | void setString(std::string_view inString); 16 | std::string getString() const; 17 | 18 | private: 19 | std::string doubleToString(double inValue) const; 20 | double stringToDouble(std::string_view inString) const; 21 | 22 | double mValue; 23 | }; 24 | -------------------------------------------------------------------------------- /c08_code/09_SpreadsheetCellArrayNoDefaultCtor/SpreadsheetCellArrayNoDefault.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | 3 | int main() 4 | { 5 | // Comment out these next two lines to test the third line 6 | SpreadsheetCell cells[3]; // FAILS compilation without a default constructor 7 | SpreadsheetCell* myCellp = new SpreadsheetCell[10]; // also FAILS 8 | 9 | // This line compiles without a default constructor 10 | SpreadsheetCell cells[3] = {SpreadsheetCell(0), SpreadsheetCell(23), 11 | SpreadsheetCell(41)}; 12 | 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /c08_code/10_SpreadsheetCellDefaultCtor/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell(); 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | 13 | void setValue(double inValue); 14 | double getValue() const; 15 | 16 | void setString(std::string_view inString); 17 | std::string getString() const; 18 | 19 | private: 20 | std::string doubleToString(double inValue) const; 21 | double stringToDouble(std::string_view inString) const; 22 | 23 | double mValue; 24 | }; 25 | -------------------------------------------------------------------------------- /c08_code/10_SpreadsheetCellDefaultCtor/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | SpreadsheetCell myCell; 10 | myCell.setValue(6); 11 | cout << "cell 1: " << myCell.getValue() << endl; 12 | 13 | auto smartCellp = make_unique(); 14 | // Or with a raw pointer (not recommended) 15 | SpreadsheetCell* myCellp = new SpreadsheetCell(); 16 | // Or 17 | // SpreadsheetCell* myCellp = new SpreadsheetCell; 18 | // ... use myCellp 19 | delete myCellp; myCellp = nullptr; 20 | 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /c08_code/11_SpreadsheetCellExplicitlyDefaulted/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell() = default; 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | 13 | void setValue(double inValue); 14 | double getValue() const; 15 | 16 | void setString(std::string_view inString); 17 | std::string getString() const; 18 | 19 | private: 20 | std::string doubleToString(double inValue) const; 21 | double stringToDouble(std::string_view inString) const; 22 | 23 | double mValue = 0; 24 | }; 25 | -------------------------------------------------------------------------------- /c08_code/11_SpreadsheetCellExplicitlyDefaulted/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | SpreadsheetCell myCell; 10 | myCell.setValue(6); 11 | cout << "cell 1: " << myCell.getValue() << endl; 12 | 13 | auto smartCellp = make_unique(); 14 | // Or with a raw pointer (not recommended) 15 | SpreadsheetCell* myCellp = new SpreadsheetCell(); 16 | // Or 17 | // SpreadsheetCell* myCellp = new SpreadsheetCell; 18 | // ... use myCellp 19 | delete myCellp; myCellp = nullptr; 20 | 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /c08_code/12_SpreadsheetCellCtorInitializer/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell() = default; 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | 13 | void setValue(double inValue); 14 | double getValue() const; 15 | 16 | void setString(std::string_view inString); 17 | std::string getString() const; 18 | 19 | private: 20 | std::string doubleToString(double inValue) const; 21 | double stringToDouble(std::string_view inString) const; 22 | 23 | double mValue = 0; 24 | }; 25 | -------------------------------------------------------------------------------- /c08_code/12_SpreadsheetCellCtorInitializer/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | SpreadsheetCell myCell; 10 | myCell.setValue(6); 11 | cout << "cell 1: " << myCell.getValue() << endl; 12 | 13 | auto smartCellp = make_unique(); 14 | // Or with a raw pointer (not recommended) 15 | SpreadsheetCell* myCellp = new SpreadsheetCell(); 16 | // Or 17 | // SpreadsheetCell* myCellp = new SpreadsheetCell; 18 | // ... use myCellp 19 | delete myCellp; myCellp = nullptr; 20 | 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /c08_code/13_CtorInitializerOrder/CtorInitializerOrder.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | class Foo 6 | { 7 | public: 8 | Foo(double value); 9 | 10 | private: 11 | double mValue; 12 | }; 13 | 14 | Foo::Foo(double value) : mValue(value) 15 | { 16 | cout << "Foo::mValue = " << mValue << endl; 17 | } 18 | 19 | class MyClass 20 | { 21 | public: 22 | MyClass(double value); 23 | 24 | private: 25 | double mValue; 26 | Foo mFoo; 27 | }; 28 | 29 | MyClass::MyClass(double value) 30 | : mValue(value) 31 | , mFoo(mValue) 32 | { 33 | cout << "MyClass::mValue = " << mValue << endl; 34 | } 35 | 36 | int main() 37 | { 38 | MyClass instance(1.2); 39 | return 0; 40 | } -------------------------------------------------------------------------------- /c08_code/14_SpreadsheetCellCopyCtor/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell() = default; 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | SpreadsheetCell(const SpreadsheetCell& src); 13 | 14 | void setValue(double inValue); 15 | double getValue() const; 16 | 17 | void setString(std::string_view inString); 18 | std::string getString() const; 19 | 20 | private: 21 | std::string doubleToString(double inValue) const; 22 | double stringToDouble(std::string_view inString) const; 23 | 24 | double mValue = 0; 25 | }; 26 | -------------------------------------------------------------------------------- /c08_code/14_SpreadsheetCellCopyCtor/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell myCell1(4); 9 | SpreadsheetCell myCell2(myCell1); 10 | // myCell2 has the same values as myCell1 11 | 12 | cout << "Cell 1: " << myCell1.getValue() << endl; 13 | cout << "Cell 2: " << myCell2.getValue() << endl; 14 | 15 | return 0; 16 | } 17 | -------------------------------------------------------------------------------- /c08_code/16_Destructors/DestructorExamples.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell myCell(5); 9 | 10 | if (myCell.getValue() == 5) { 11 | SpreadsheetCell anotherCell(6); 12 | } // anotherCell is destroyed as this block ends 13 | 14 | cout << "myCell: " << myCell.getValue() << endl; 15 | 16 | { 17 | SpreadsheetCell myCell2(4); 18 | SpreadsheetCell anotherCell2(5); // myCell2 constructed before anotherCell2 19 | } // anotherCell2 destroyed before myCell2 20 | 21 | return 0; 22 | } // myCell is destroyed as this block ends 23 | -------------------------------------------------------------------------------- /c08_code/16_Destructors/DestructorHeapExamples.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell* cellPtr1 = new SpreadsheetCell(5); 9 | SpreadsheetCell* cellPtr2 = new SpreadsheetCell(6); 10 | 11 | cout << "cellPtr1: " << cellPtr1->getValue() << endl; 12 | 13 | delete cellPtr1; // destroys cellPtr1 14 | cellPtr1 = nullptr; 15 | 16 | return 0; 17 | } // cellPtr2 is NOT destroyed because delete was not called on it 18 | -------------------------------------------------------------------------------- /c08_code/16_Destructors/README.txt: -------------------------------------------------------------------------------- 1 | Two source files in this directory include a main() function. Your project 2 | should include SpreadsheetCell.cpp and one of DestructorExamples.cpp or 3 | DestructorHeapExamples.cpp. 4 | 5 | 6 | -------------------------------------------------------------------------------- /c08_code/16_Destructors/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell() = default; 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | SpreadsheetCell(const SpreadsheetCell& src); 13 | 14 | void setValue(double inValue); 15 | double getValue() const; 16 | 17 | void setString(std::string_view inString); 18 | std::string getString() const; 19 | 20 | private: 21 | std::string doubleToString(double inValue) const; 22 | double stringToDouble(std::string_view inString) const; 23 | 24 | double mValue = 0; 25 | }; 26 | -------------------------------------------------------------------------------- /c08_code/17_SpreadsheetCellAssign/README.txt: -------------------------------------------------------------------------------- 1 | Two source files in this directory include a main() function. Your project 2 | should include SpreadsheetCell.cpp and either SpreadsheetCellTest.cpp or 3 | SpreadsheetCellAssignCopy.cpp 4 | 5 | -------------------------------------------------------------------------------- /c08_code/17_SpreadsheetCellAssign/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell() = default; 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | SpreadsheetCell(const SpreadsheetCell& src); 13 | 14 | SpreadsheetCell& operator=(const SpreadsheetCell& rhs); 15 | 16 | void setValue(double inValue); 17 | double getValue() const; 18 | 19 | void setString(std::string_view inString); 20 | std::string getString() const; 21 | 22 | private: 23 | std::string doubleToString(double inValue) const; 24 | double stringToDouble(std::string_view inString) const; 25 | 26 | double mValue = 0; 27 | }; 28 | -------------------------------------------------------------------------------- /c08_code/17_SpreadsheetCellAssign/SpreadsheetCellAssignCopy.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell myCell(5); 9 | SpreadsheetCell anotherCell(myCell); 10 | SpreadsheetCell aThirdCell = myCell; 11 | anotherCell = myCell; // Calls operator= for anotherCell. 12 | 13 | SpreadsheetCell myCell2(5); 14 | string s1; 15 | s1 = myCell2.getString(); 16 | 17 | SpreadsheetCell myCell3(5); 18 | string s2 = myCell3.getString(); 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c08_code/17_SpreadsheetCellAssign/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | 3 | int main() 4 | { 5 | SpreadsheetCell myCell, anotherCell, aThirdCell; 6 | 7 | myCell = anotherCell = aThirdCell; 8 | myCell.operator=(anotherCell.operator=(aThirdCell)); 9 | 10 | SpreadsheetCell cell(4); 11 | cell = cell; // self-assignment 12 | 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /c08_code/README.txt: -------------------------------------------------------------------------------- 1 | Unless otherwise noted, include all .cpp files in a subdirectory in your project. 2 | -------------------------------------------------------------------------------- /c09_code/01_Spreadsheet/Spreadsheet.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include "SpreadsheetCell.h" 5 | 6 | class Spreadsheet 7 | { 8 | public: 9 | Spreadsheet(size_t width, size_t height); 10 | Spreadsheet(const Spreadsheet& src); 11 | ~Spreadsheet(); 12 | 13 | Spreadsheet& operator=(const Spreadsheet& rhs); 14 | 15 | void setCellAt(size_t x, size_t y, const SpreadsheetCell& cell); 16 | SpreadsheetCell& getCellAt(size_t x, size_t y); 17 | 18 | friend void swap(Spreadsheet& first, Spreadsheet& second) noexcept; 19 | 20 | private: 21 | void verifyCoordinate(size_t x, size_t y) const; 22 | 23 | size_t mWidth = 0; 24 | size_t mHeight = 0; 25 | SpreadsheetCell** mCells = nullptr; 26 | }; 27 | -------------------------------------------------------------------------------- /c09_code/01_Spreadsheet/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell() = default; 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | 13 | void setValue(double inValue); 14 | double getValue() const; 15 | 16 | void setString(std::string_view inString); 17 | std::string getString() const; 18 | 19 | private: 20 | std::string doubleToString(double inValue) const; 21 | double stringToDouble(std::string_view inString) const; 22 | 23 | double mValue = 0; 24 | }; 25 | -------------------------------------------------------------------------------- /c09_code/01_Spreadsheet/SpreadsheetTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Spreadsheet.h" 2 | 3 | void printSpreadsheet(Spreadsheet s) 4 | { 5 | // code omitted for brevity 6 | } 7 | 8 | int main() 9 | { 10 | //Spreadsheet s1(4, 3); 11 | //printSpreadsheet(s1); 12 | 13 | Spreadsheet s1(2, 2), s2(4, 3); 14 | s1 = s2; 15 | 16 | return 0; 17 | } 18 | -------------------------------------------------------------------------------- /c09_code/02_SpreadsheetNoCopyAssign/README.txt: -------------------------------------------------------------------------------- 1 | SpreadsheetTest.cpp does not compile. 2 | -------------------------------------------------------------------------------- /c09_code/02_SpreadsheetNoCopyAssign/Spreadsheet.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include "SpreadsheetCell.h" 5 | 6 | class Spreadsheet 7 | { 8 | public: 9 | Spreadsheet(size_t width, size_t height); 10 | Spreadsheet(const Spreadsheet& src) = delete; 11 | ~Spreadsheet(); 12 | 13 | Spreadsheet& operator=(const Spreadsheet& rhs) = delete; 14 | 15 | void setCellAt(size_t x, size_t y, const SpreadsheetCell& cell); 16 | SpreadsheetCell& getCellAt(size_t x, size_t y); 17 | 18 | friend void swap(Spreadsheet& first, Spreadsheet& second) noexcept; 19 | 20 | private: 21 | void verifyCoordinate(size_t x, size_t y) const; 22 | 23 | size_t mWidth = 0; 24 | size_t mHeight = 0; 25 | SpreadsheetCell** mCells = nullptr; 26 | }; 27 | -------------------------------------------------------------------------------- /c09_code/02_SpreadsheetNoCopyAssign/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell() = default; 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | 13 | void setValue(double inValue); 14 | double getValue() const; 15 | 16 | void setString(std::string_view inString); 17 | std::string getString() const; 18 | 19 | private: 20 | std::string doubleToString(double inValue) const; 21 | double stringToDouble(std::string_view inString) const; 22 | 23 | double mValue = 0; 24 | }; 25 | -------------------------------------------------------------------------------- /c09_code/02_SpreadsheetNoCopyAssign/SpreadsheetTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Spreadsheet.h" 2 | 3 | void printSpreadsheet(Spreadsheet s) 4 | { 5 | // code omitted for brevity 6 | } 7 | 8 | int main() 9 | { 10 | //Spreadsheet s1(4, 3); 11 | //printSpreadsheet(s1); 12 | 13 | Spreadsheet s1(2, 2), s2(4, 3); 14 | s1 = s2; 15 | 16 | return 0; 17 | } 18 | -------------------------------------------------------------------------------- /c09_code/04_SpreadsheetMoveSemantics/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell() = default; 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | 13 | void setValue(double inValue); 14 | double getValue() const; 15 | 16 | void setString(std::string_view inString); 17 | std::string getString() const; 18 | 19 | private: 20 | std::string doubleToString(double inValue) const; 21 | double stringToDouble(std::string_view inString) const; 22 | 23 | double mValue = 0; 24 | }; 25 | -------------------------------------------------------------------------------- /c09_code/04_SpreadsheetMoveSemantics/SpreadsheetTest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include "Spreadsheet.h" 4 | 5 | using namespace std; 6 | 7 | Spreadsheet createObject() 8 | { 9 | return Spreadsheet(3, 2); 10 | } 11 | 12 | int main() 13 | { 14 | vector vec; 15 | for (int i = 0; i < 2; ++i) { 16 | cout << "Iteration " << i << endl; 17 | vec.push_back(Spreadsheet(100, 100)); 18 | cout << endl; 19 | } 20 | 21 | Spreadsheet s(2,3); 22 | s = createObject(); 23 | 24 | Spreadsheet s2(5,6); 25 | s2 = s; 26 | 27 | return 0; 28 | } 29 | -------------------------------------------------------------------------------- /c09_code/05_SpreadsheetMoveSemanticsWithSwap/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell() = default; 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | 13 | void setValue(double inValue); 14 | double getValue() const; 15 | 16 | void setString(std::string_view inString); 17 | std::string getString() const; 18 | 19 | private: 20 | std::string doubleToString(double inValue) const; 21 | double stringToDouble(std::string_view inString) const; 22 | 23 | double mValue = 0; 24 | }; 25 | -------------------------------------------------------------------------------- /c09_code/05_SpreadsheetMoveSemanticsWithSwap/SpreadsheetTest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include "Spreadsheet.h" 4 | 5 | using namespace std; 6 | 7 | Spreadsheet createObject() 8 | { 9 | return Spreadsheet(3, 2); 10 | } 11 | 12 | int main() 13 | { 14 | vector vec; 15 | for (int i = 0; i < 2; ++i) { 16 | cout << "Iteration " << i << endl; 17 | vec.push_back(Spreadsheet(100, 100)); 18 | cout << endl; 19 | } 20 | 21 | Spreadsheet s(2,3); 22 | s = createObject(); 23 | 24 | Spreadsheet s2(5,6); 25 | s2 = s; 26 | 27 | return 0; 28 | } 29 | -------------------------------------------------------------------------------- /c09_code/06_SpreadsheetCellMethods/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | string str = SpreadsheetCell::doubleToString(5); 9 | 10 | SpreadsheetCell myCell(5); 11 | cout << myCell.getValue() << endl; // OK 12 | myCell.set("6"); // OK 13 | 14 | const SpreadsheetCell& myCellConstRef = myCell; 15 | cout << myCellConstRef.getValue() << endl; // OK 16 | //myCellConstRef.set("6"); // Compilation Error! 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c09_code/07_SpreadsheetConstGetCellAt/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell() = default; 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | 13 | void setValue(double inValue); 14 | double getValue() const; 15 | 16 | void setString(std::string_view inString); 17 | std::string getString() const; 18 | 19 | private: 20 | std::string doubleToString(double inValue) const; 21 | double stringToDouble(std::string_view inString) const; 22 | 23 | double mValue = 0; 24 | }; 25 | -------------------------------------------------------------------------------- /c09_code/07_SpreadsheetConstGetCellAt/SpreadsheetTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Spreadsheet.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | Spreadsheet sheet1(5, 6); 9 | SpreadsheetCell& cell1 = sheet1.getCellAt(1, 1); 10 | 11 | const Spreadsheet sheet2(5, 6); 12 | const SpreadsheetCell& cell2 = sheet2.getCellAt(1, 1); 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c09_code/08_SpreadsheetDefaultArguments/Spreadsheet.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include "SpreadsheetCell.h" 5 | 6 | class Spreadsheet 7 | { 8 | public: 9 | Spreadsheet(size_t width = 100, size_t height = 100); 10 | Spreadsheet(const Spreadsheet& src); 11 | ~Spreadsheet(); 12 | 13 | Spreadsheet& operator=(const Spreadsheet& rhs); 14 | 15 | void setCellAt(size_t x, size_t y, const SpreadsheetCell& cell); 16 | SpreadsheetCell& getCellAt(size_t x, size_t y); 17 | 18 | friend void swap(Spreadsheet& first, Spreadsheet& second) noexcept; 19 | 20 | private: 21 | void verifyCoordinate(size_t x, size_t y) const; 22 | 23 | size_t mWidth = 0; 24 | size_t mHeight = 0; 25 | SpreadsheetCell** mCells = nullptr; 26 | }; 27 | -------------------------------------------------------------------------------- /c09_code/08_SpreadsheetDefaultArguments/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell() = default; 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | 13 | void setValue(double inValue); 14 | double getValue() const; 15 | 16 | void setString(std::string_view inString); 17 | std::string getString() const; 18 | 19 | private: 20 | std::string doubleToString(double inValue) const; 21 | double stringToDouble(std::string_view inString) const; 22 | 23 | double mValue = 0; 24 | }; 25 | -------------------------------------------------------------------------------- /c09_code/08_SpreadsheetDefaultArguments/SpreadsheetTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Spreadsheet.h" 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | Spreadsheet s1; 8 | Spreadsheet s2(5); 9 | Spreadsheet s3(5, 6); 10 | 11 | return 0; 12 | } 13 | -------------------------------------------------------------------------------- /c09_code/09_SpreadsheetDataMembers/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | SpreadsheetCell() = default; 10 | SpreadsheetCell(double initialValue); 11 | SpreadsheetCell(std::string_view initialValue); 12 | 13 | void setValue(double inValue); 14 | double getValue() const; 15 | 16 | void setString(std::string_view inString); 17 | std::string getString() const; 18 | 19 | private: 20 | std::string doubleToString(double inValue) const; 21 | double stringToDouble(std::string_view inString) const; 22 | 23 | double mValue = 0; 24 | }; 25 | -------------------------------------------------------------------------------- /c09_code/09_SpreadsheetDataMembers/SpreadsheetTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Spreadsheet.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | class SpreadsheetApplication {}; 7 | 8 | int main() 9 | { 10 | SpreadsheetApplication app; 11 | Spreadsheet s1(2, 3, app); 12 | Spreadsheet s2(3, 4, app); 13 | 14 | cout << "Maximum height is: " << Spreadsheet::kMaxHeight << endl; 15 | 16 | return 0; 17 | } 18 | -------------------------------------------------------------------------------- /c09_code/10_NestedClasses/SpreadsheetTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Spreadsheet.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | class SpreadsheetApplication {}; 7 | 8 | int main() 9 | { 10 | SpreadsheetApplication theApp; 11 | Spreadsheet s1(5, 6, theApp); 12 | 13 | Spreadsheet::Cell c1(4), c2(5); 14 | Spreadsheet::Cell c3(c1); 15 | c2 = c3; 16 | 17 | cout << c1.getValue() << endl; 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c09_code/11_SpreadsheetCellColors/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | SpreadsheetCell myCell(5); 8 | myCell.setColor(SpreadsheetCell::Color::Blue); 9 | auto color = myCell.getColor(); 10 | 11 | return 0; 12 | } 13 | -------------------------------------------------------------------------------- /c09_code/12_OperatorOverloading/AddFirstAttempt/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell myCell(4), anotherCell(5); 9 | SpreadsheetCell aThirdCell = myCell.add(anotherCell); 10 | cout << aThirdCell.getValue() << endl; 11 | 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c09_code/12_OperatorOverloading/AddSecondAttempt/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | SpreadsheetCell myCell(4), anotherCell(5); 8 | SpreadsheetCell aThirdCell = myCell + anotherCell; 9 | //SpreadsheetCell aThirdCell = myCell.operator+(anotherCell); 10 | 11 | string str = "hello"; 12 | 13 | aThirdCell = myCell + string_view(str); 14 | aThirdCell = myCell + 5.6; 15 | aThirdCell = myCell + 4; 16 | 17 | // The following two lines don't compile 18 | // aThirdCell = 4 + myCell; // FAILS TO COMPILE! 19 | // aThirdCell = 5.6 + myCell; // FAILS TO COMPILE! 20 | 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /c09_code/13_SeparateImpl/SpreadsheetTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Spreadsheet.h" 2 | 3 | using namespace std; 4 | 5 | class SpreadsheetApplication {}; 6 | 7 | int main() 8 | { 9 | SpreadsheetApplication theApp; 10 | Spreadsheet s1(theApp); 11 | Spreadsheet s3(theApp, 5, 6); 12 | Spreadsheet s4(s3); 13 | s1 = s4; 14 | 15 | return 0; 16 | } 17 | -------------------------------------------------------------------------------- /c09_code/README.txt: -------------------------------------------------------------------------------- 1 | Unless otherwise noted, include all .cpp files in a subdirectory in your 2 | project. 3 | -------------------------------------------------------------------------------- /c10_code/01_WeatherPrediction/MyWeatherPrediction.cpp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/HodongMan/professional-cpp-4th-ed/301d835f3a7df790e4873bcf8c797f5711b4d932/c10_code/01_WeatherPrediction/MyWeatherPrediction.cpp -------------------------------------------------------------------------------- /c10_code/01_WeatherPrediction/MyWeatherPrediction.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "WeatherPrediction.h" 4 | 5 | class MyWeatherPrediction : public WeatherPrediction 6 | { 7 | public: 8 | virtual void setCurrentTempCelsius(int temp); 9 | 10 | virtual int getTomorrowTempCelsius() const; 11 | 12 | virtual void showResult() const override; 13 | 14 | virtual std::string getTemperature() const override; 15 | 16 | private: 17 | static int convertCelsiusToFahrenheit(int celsius); 18 | static int convertFahrenheitToCelsius(int fahrenheit); 19 | }; 20 | -------------------------------------------------------------------------------- /c10_code/02_ConstructorChain/ConstructorChain.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | class Something 6 | { 7 | public: 8 | Something() { cout << "2"; } 9 | virtual ~Something() { cout << "2"; } 10 | }; 11 | 12 | class Base 13 | { 14 | public: 15 | Base() { cout << "1"; } 16 | virtual ~Base() { cout << "1"; } 17 | }; 18 | 19 | class Derived : public Base 20 | { 21 | public: 22 | Derived() { cout << "3"; } 23 | virtual ~Derived() { cout << "3"; } 24 | 25 | private: 26 | Something mDataMember; 27 | }; 28 | 29 | int main() 30 | { 31 | Derived myDerived; 32 | return 0; 33 | } 34 | -------------------------------------------------------------------------------- /c10_code/04_PolymorphicSpreadsheet/DoubleSpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "SpreadsheetCell.h" 4 | #include 5 | 6 | class DoubleSpreadsheetCell : public SpreadsheetCell 7 | { 8 | public: 9 | virtual void set(double inDouble); 10 | virtual void set(std::string_view inString) override; 11 | 12 | virtual std::string getString() const override; 13 | 14 | private: 15 | static std::string doubleToString(double inValue); 16 | static double stringToDouble(std::string_view inValue); 17 | 18 | std::optional mValue; 19 | }; 20 | -------------------------------------------------------------------------------- /c10_code/04_PolymorphicSpreadsheet/SpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | class SpreadsheetCell 7 | { 8 | public: 9 | virtual ~SpreadsheetCell() = default; 10 | 11 | virtual void set(std::string_view inString) = 0; 12 | 13 | virtual std::string getString() const = 0; 14 | }; 15 | -------------------------------------------------------------------------------- /c10_code/04_PolymorphicSpreadsheet/StringSpreadsheetCell.cpp: -------------------------------------------------------------------------------- 1 | #include "StringSpreadsheetCell.h" 2 | 3 | using namespace std; 4 | 5 | StringSpreadsheetCell::StringSpreadsheetCell(const DoubleSpreadsheetCell& inDoubleCell) 6 | { 7 | mValue = inDoubleCell.getString(); 8 | } 9 | 10 | void StringSpreadsheetCell::set(string_view inString) 11 | { 12 | mValue = inString; 13 | } 14 | 15 | string StringSpreadsheetCell::getString() const 16 | { 17 | return mValue.value_or(""); 18 | } 19 | -------------------------------------------------------------------------------- /c10_code/04_PolymorphicSpreadsheet/StringSpreadsheetCell.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "SpreadsheetCell.h" 4 | #include 5 | #include "DoubleSpreadsheetCell.h" 6 | 7 | class StringSpreadsheetCell : public SpreadsheetCell 8 | { 9 | public: 10 | StringSpreadsheetCell() = default; 11 | StringSpreadsheetCell(const DoubleSpreadsheetCell& inDoubleCell); 12 | 13 | virtual void set(std::string_view inString) override; 14 | 15 | virtual std::string getString() const override; 16 | 17 | private: 18 | std::optional mValue; 19 | }; 20 | -------------------------------------------------------------------------------- /c10_code/05_DogBird/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | 3 | -------------------------------------------------------------------------------- /c10_code/06_Cherry/BingCherry.cpp: -------------------------------------------------------------------------------- 1 | #include "BingCherry.h" 2 | #include 3 | 4 | void BingCherry::printType() 5 | { 6 | std::cout << "I am a Bing Cherry" << std::endl; 7 | } 8 | 9 | void BingCherry::polish() 10 | { 11 | std::cout << "I am getting polished" << std::endl; 12 | } 13 | -------------------------------------------------------------------------------- /c10_code/06_Cherry/BingCherry.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "Cherry.h" 4 | 5 | class BingCherry : public Cherry 6 | { 7 | public: 8 | virtual void printType() override; 9 | 10 | virtual void polish(); 11 | }; 12 | -------------------------------------------------------------------------------- /c10_code/06_Cherry/BingCherryTree.cpp: -------------------------------------------------------------------------------- 1 | #include "BingCherryTree.h" 2 | #include 3 | 4 | BingCherry* BingCherryTree::pick() 5 | { 6 | auto theCherry = std::make_unique(); 7 | theCherry->polish(); 8 | return theCherry.release(); 9 | } 10 | -------------------------------------------------------------------------------- /c10_code/06_Cherry/BingCherryTree.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "CherryTree.h" 4 | #include "BingCherry.h" 5 | 6 | class BingCherryTree : public CherryTree 7 | { 8 | public: 9 | virtual BingCherry* pick() override; 10 | }; 11 | -------------------------------------------------------------------------------- /c10_code/06_Cherry/Cherry.cpp: -------------------------------------------------------------------------------- 1 | #include "Cherry.h" 2 | #include 3 | 4 | void Cherry::printType() 5 | { 6 | std::cout << "I am a Cherry" << std::endl; 7 | } 8 | -------------------------------------------------------------------------------- /c10_code/06_Cherry/Cherry.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | class Cherry 4 | { 5 | public: 6 | virtual void printType(); 7 | }; 8 | -------------------------------------------------------------------------------- /c10_code/06_Cherry/CherryTree.cpp: -------------------------------------------------------------------------------- 1 | #include "CherryTree.h" 2 | 3 | Cherry* CherryTree::pick() 4 | { 5 | return new Cherry(); 6 | } 7 | -------------------------------------------------------------------------------- /c10_code/06_Cherry/CherryTree.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "Cherry.h" 4 | 5 | class CherryTree 6 | { 7 | public: 8 | virtual Cherry* pick(); 9 | }; 10 | -------------------------------------------------------------------------------- /c10_code/06_Cherry/TestCherry.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include "BingCherry.h" 4 | #include "BingCherryTree.h" 5 | 6 | int main() 7 | { 8 | BingCherryTree theTree; 9 | std::unique_ptr theCherry(theTree.pick()); 10 | theCherry->printType(); 11 | 12 | return 0; 13 | } 14 | 15 | -------------------------------------------------------------------------------- /c10_code/07_MilesEstimator/EfficientCarMilesEstimator.cpp: -------------------------------------------------------------------------------- 1 | #include "EfficientCarMilesEstimator.h" 2 | 3 | int EfficientCarMilesEstimator::getMilesPerGallon() const 4 | { 5 | return 35; 6 | } 7 | -------------------------------------------------------------------------------- /c10_code/07_MilesEstimator/EfficientCarMilesEstimator.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "MilesEstimator.h" 4 | 5 | class EfficientCarMilesEstimator : public MilesEstimator 6 | { 7 | private: 8 | virtual int getMilesPerGallon() const override; 9 | }; 10 | -------------------------------------------------------------------------------- /c10_code/07_MilesEstimator/MilesEstimator.cpp: -------------------------------------------------------------------------------- 1 | #include "MilesEstimator.h" 2 | 3 | int MilesEstimator::getMilesLeft() const 4 | { 5 | return getMilesPerGallon() * getGallonsLeft(); 6 | } 7 | 8 | void MilesEstimator::setGallonsLeft(int gallons) 9 | { 10 | mGallonsLeft = gallons; 11 | } 12 | 13 | int MilesEstimator::getGallonsLeft() const 14 | { 15 | return mGallonsLeft; 16 | } 17 | 18 | int MilesEstimator::getMilesPerGallon() const 19 | { 20 | return 20; 21 | } 22 | -------------------------------------------------------------------------------- /c10_code/07_MilesEstimator/MilesEstimator.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | 5 | class MilesEstimator 6 | { 7 | public: 8 | virtual ~MilesEstimator() = default; 9 | 10 | virtual int getMilesLeft() const; 11 | 12 | virtual void setGallonsLeft(int gallons); 13 | virtual int getGallonsLeft() const; 14 | 15 | private: 16 | int mGallonsLeft; 17 | virtual int getMilesPerGallon() const; 18 | }; 19 | -------------------------------------------------------------------------------- /c10_code/07_MilesEstimator/TestMilesEstimator.cpp: -------------------------------------------------------------------------------- 1 | #include "EfficientCarMilesEstimator.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | MilesEstimator myMilesEstimator; 9 | myMilesEstimator.setGallonsLeft(2); 10 | cout << "Normal estimator can go " << myMilesEstimator.getMilesLeft() 11 | << " more miles." << endl; 12 | 13 | EfficientCarMilesEstimator myEstimator; 14 | myEstimator.setGallonsLeft(2); 15 | cout << "Efficient estimator can go " << myEstimator.getMilesLeft() 16 | << " more miles." << endl; 17 | 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c11_code/01_References/02_ReferenceDataMembers.cpp: -------------------------------------------------------------------------------- 1 | class MyClass 2 | { 3 | public: 4 | MyClass(int& ref) : mRef(ref) {} 5 | 6 | private: 7 | int& mRef; 8 | }; 9 | 10 | int main() 11 | { 12 | int i = 123; 13 | MyClass m(i); 14 | 15 | return 0; 16 | } 17 | -------------------------------------------------------------------------------- /c11_code/01_References/03_ReferenceParameters.cpp: -------------------------------------------------------------------------------- 1 | void swap(int& first, int& second) 2 | { 3 | int temp = first; 4 | first = second; 5 | second = temp; 6 | } 7 | 8 | int main() 9 | { 10 | int x = 5, y = 6; 11 | swap(x, y); 12 | 13 | // swap(3, 4); // DOES NOT COMPILE 14 | 15 | int *xp = &x, *yp = &y; 16 | swap(*xp, *yp); 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c11_code/01_References/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c11_code/03_Constexpr/01_constexpr.cpp: -------------------------------------------------------------------------------- 1 | constexpr int getArraySize() 2 | { 3 | return 32; 4 | } 5 | 6 | int main() 7 | { 8 | int myArray[getArraySize()]; // OK 9 | myArray[0] = 1; 10 | return 0; 11 | } 12 | -------------------------------------------------------------------------------- /c11_code/03_Constexpr/02_constexprClasses.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | class Rect 8 | { 9 | public: 10 | constexpr Rect(size_t width, size_t height) 11 | : mWidth(width), mHeight(height) 12 | { 13 | } 14 | 15 | constexpr size_t getArea() const 16 | { 17 | return mWidth * mHeight; 18 | } 19 | 20 | private: 21 | size_t mWidth, mHeight; 22 | }; 23 | 24 | int main() 25 | { 26 | constexpr Rect r(8, 2); 27 | int myArray[r.getArea()]; 28 | cout << std::size(myArray) << endl; 29 | 30 | return 0; 31 | } -------------------------------------------------------------------------------- /c11_code/03_Constexpr/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c11_code/04_Static/AnotherFile.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | void f(); 4 | //static void f(); 5 | 6 | void f() 7 | { 8 | std::cout << "f\n"; 9 | } 10 | -------------------------------------------------------------------------------- /c11_code/04_Static/FirstFile.cpp: -------------------------------------------------------------------------------- 1 | void f(); 2 | 3 | int main() 4 | { 5 | f(); 6 | return 0; 7 | } 8 | -------------------------------------------------------------------------------- /c11_code/04_Static/README.txt: -------------------------------------------------------------------------------- 1 | Compile AnotherFile.cpp and FirstFile.cpp together. 2 | -------------------------------------------------------------------------------- /c11_code/05_AnonymousNamespaces/AnotherFile.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | namespace { 4 | void f(); 5 | 6 | void f() 7 | { 8 | std::cout << "f\n"; 9 | } 10 | } 11 | -------------------------------------------------------------------------------- /c11_code/05_AnonymousNamespaces/FirstFile.cpp: -------------------------------------------------------------------------------- 1 | void f(); 2 | 3 | int main() 4 | { 5 | f(); 6 | return 0; 7 | } 8 | -------------------------------------------------------------------------------- /c11_code/05_AnonymousNamespaces/README.txt: -------------------------------------------------------------------------------- 1 | Compile AnotherFile.cpp and FirstFile.cpp together. 2 | 3 | 4 | Notes: 5 | AnotherFile.cpp and FirstFile.cpp will fail at the link stage. 6 | -------------------------------------------------------------------------------- /c11_code/06_Extern/AnotherFile.cpp: -------------------------------------------------------------------------------- 1 | extern int x; 2 | int x = 3; 3 | 4 | //extern int x = 3; 5 | -------------------------------------------------------------------------------- /c11_code/06_Extern/FirstFile.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | extern int x; 4 | 5 | int main() 6 | { 7 | std::cout << x << std::endl; 8 | 9 | return 0; 10 | } 11 | -------------------------------------------------------------------------------- /c11_code/06_Extern/README.txt: -------------------------------------------------------------------------------- 1 | Compile AnotherFile.cpp and FirstFile.cpp together. 2 | -------------------------------------------------------------------------------- /c11_code/07_StaticsInFunctions/StaticsInFunctions.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | void performTask() 6 | { 7 | static bool initialized = false; 8 | 9 | if (!initialized) { 10 | cout << "initializing" << endl; 11 | // Perform initialization. 12 | initialized = true; 13 | } 14 | 15 | // Perform the desired task. 16 | } 17 | 18 | int main() 19 | { 20 | performTask(); 21 | performTask(); 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c11_code/08_Order/order.cpp: -------------------------------------------------------------------------------- 1 | class Demo 2 | { 3 | public: 4 | static int x; 5 | }; 6 | 7 | int Demo::x = 3; 8 | int y = 4; 9 | 10 | 11 | int main() 12 | { 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /c11_code/09_TypeAliases/TypeAliases.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | //void processVector(const std::vector& vec) 5 | //{ 6 | // // Body omitted 7 | //} 8 | 9 | using StringVector = std::vector; 10 | 11 | void processVector(const StringVector& vec) 12 | { 13 | // Body omitted 14 | } 15 | 16 | int main() 17 | { 18 | //std::vector myVector; 19 | StringVector myVector; 20 | processVector(myVector); 21 | // Rest of the program ... 22 | return 0; 23 | } 24 | -------------------------------------------------------------------------------- /c11_code/11_PtrsToMethodsAndMembers/PtrsToMethodsAndMembers.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include "Employee.h" 3 | 4 | using namespace std; 5 | using namespace Records; 6 | 7 | int main() 8 | { 9 | Employee employee; 10 | 11 | // Old style: 12 | //int (Employee::*methodPtr) () const = &Employee::getSalary; 13 | 14 | // Using a type alias: 15 | //using PtrToGet = int (Employee::*) () const; 16 | //PtrToGet methodPtr = &Employee::getSalary; 17 | 18 | // Using auto: 19 | auto methodPtr = &Employee::getSalary; 20 | 21 | cout << (employee.*methodPtr)() << endl; 22 | 23 | return 0; 24 | } -------------------------------------------------------------------------------- /c11_code/12_Casts/01_ConstCast.cpp: -------------------------------------------------------------------------------- 1 | extern void ThirdPartyLibraryMethod(char* str); 2 | 3 | void f(const char* str) 4 | { 5 | ThirdPartyLibraryMethod(const_cast(str)); 6 | } 7 | 8 | int main() 9 | { 10 | f("Hello World"); 11 | 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c11_code/12_Casts/02_StaticCast.cpp: -------------------------------------------------------------------------------- 1 | class Base 2 | { 3 | public: 4 | virtual ~Base() = default; 5 | }; 6 | 7 | class Derived : public Base 8 | { 9 | public: 10 | virtual ~Derived() = default; 11 | }; 12 | 13 | int main() 14 | { 15 | int i = 3; 16 | int j = 4; 17 | double result = static_cast(i) / j; 18 | 19 | 20 | Base* b; 21 | Derived* d = new Derived(); 22 | 23 | b = d; // Don't need a cast to go up the inheritance hierarchy 24 | d = static_cast(b); // Need a cast to go down the hierarchy 25 | 26 | Base base; 27 | Derived derived; 28 | 29 | Base& br = derived; 30 | Derived& dr = static_cast(br); 31 | 32 | return 0; 33 | } 34 | -------------------------------------------------------------------------------- /c11_code/12_Casts/03_ReinterpretCast.cpp: -------------------------------------------------------------------------------- 1 | class X {}; 2 | class Y {}; 3 | 4 | int main() 5 | { 6 | X x; 7 | Y y; 8 | 9 | X* xp = &x; 10 | Y* yp = &y; 11 | 12 | // Need reinterpret cast for pointer conversion from unrelated classes 13 | // static_cast doesn't work. 14 | xp = reinterpret_cast(yp); 15 | 16 | // No cast required for conversion from pointer to void* 17 | void* p = xp; 18 | // Need reinterpret cast for pointer conversion from void* 19 | xp = reinterpret_cast(p); 20 | 21 | // Need reinterpret cast for reference conversion from unrelated classes 22 | // static_cast doesn't work. 23 | X& xr = x; 24 | Y& yr = reinterpret_cast(x); 25 | 26 | return 0; 27 | } 28 | -------------------------------------------------------------------------------- /c11_code/12_Casts/04_DynamicCast.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | using namespace std; 4 | 5 | class Base 6 | { 7 | public: 8 | virtual ~Base() = default; 9 | }; 10 | 11 | class Derived : public Base 12 | { 13 | public: 14 | virtual ~Derived() = default; 15 | }; 16 | 17 | int main() 18 | { 19 | Base* b; 20 | Derived* d = new Derived(); 21 | 22 | b = d; 23 | d = dynamic_cast(b); 24 | 25 | Base base; 26 | Derived derived; 27 | 28 | Base& br = base; 29 | 30 | try { 31 | Derived& dr = dynamic_cast(br); 32 | } catch (const bad_cast&) { 33 | cout << "Bad cast!" << endl; 34 | } 35 | 36 | return 0; 37 | } 38 | -------------------------------------------------------------------------------- /c11_code/12_Casts/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | 3 | Note: 01_ConstCast.cpp will give a linker error. -------------------------------------------------------------------------------- /c11_code/13_Scope/Scope.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | class Demo 5 | { 6 | public: 7 | static int get() { return 5; } 8 | }; 9 | 10 | int get() { return 10; } 11 | 12 | namespace NS 13 | { 14 | int get() { return 20; } 15 | } 16 | 17 | int main() 18 | { 19 | auto pd = std::make_unique(); 20 | Demo d; 21 | std::cout << pd->get() << std::endl; // prints 5 22 | std::cout << d.get() << std::endl; // prints 5 23 | std::cout << NS::get() << std::endl; // prints 20 24 | std::cout << Demo::get() << std::endl; // prints 5 25 | std::cout << ::get() << std::endl; // prints 10 26 | std::cout << get() << std::endl; // prints 10 27 | return 0; 28 | } 29 | -------------------------------------------------------------------------------- /c11_code/16_VarArgs/01_PrintfDemo.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | int main() 4 | { 5 | printf("int %d\n", 5); 6 | printf("String %s and int %d\n", "hello", 5); 7 | printf("Many ints: %d, %d, %d, %d, %d\n", 1, 2, 3, 4, 5); 8 | return 0; 9 | } 10 | -------------------------------------------------------------------------------- /c11_code/16_VarArgs/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c11_code/17_Macros/Square.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | using namespace std; 3 | 4 | #define SQUARE(x) ((x) * (x)) // No semicolon after the macro definition! 5 | //#define SQUARE(x) (x * x) 6 | 7 | int main() 8 | { 9 | cout << SQUARE(5) << endl; 10 | cout << SQUARE(2 + 3) << endl; 11 | 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c12_code/02_Grid/03_MethodsInSource/README.txt: -------------------------------------------------------------------------------- 1 | Do not include Grid.cpp in your project. 2 | -------------------------------------------------------------------------------- /c12_code/03_GridNonType/GridTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Grid.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | constexpr size_t getHeight() 7 | { 8 | return 10; 9 | } 10 | 11 | int main() 12 | { 13 | Grid myGrid; 14 | Grid anotherGrid; 15 | 16 | myGrid.at(2, 3) = 42; 17 | anotherGrid = myGrid; 18 | 19 | cout << anotherGrid.at(2, 3).value_or(0); 20 | 21 | Grid myDoubleGrid; 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c12_code/04_GridNonTypeDefault/GridTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Grid.h" 2 | 3 | #include 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | Grid<> myIntGrid; 9 | Grid myGrid; 10 | Grid anotherGrid; 11 | Grid aFourthGrid; 12 | 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /c12_code/05_MethodTemplates/GridTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Grid.h" 2 | 3 | int main() 4 | { 5 | Grid myIntGrid(2,2); 6 | Grid myDoubleGrid; 7 | myIntGrid.at(1, 1) = 11; 8 | 9 | myDoubleGrid = myIntGrid; 10 | Grid newDoubleGrid(myIntGrid); 11 | 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c12_code/06_MethodTemplatesNonType/GridTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Grid.h" 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | Grid myIntGrid; 8 | Grid myDoubleGrid; 9 | myIntGrid.at(1, 1) = 11; 10 | 11 | myDoubleGrid = myIntGrid; 12 | Grid newDoubleGrid(myIntGrid); 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c12_code/07_GridSpecialization/GridTest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include "GridString.h" 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | Grid myIntGrid; // Uses original Grid template 10 | Grid stringGrid1(2, 2); // Uses const char* specialization 11 | 12 | const char* dummy = "dummy"; 13 | stringGrid1.at(0, 0) = "hello"; 14 | stringGrid1.at(0, 1) = dummy; 15 | stringGrid1.at(1, 0) = dummy; 16 | stringGrid1.at(1, 1) = "there"; 17 | 18 | Grid stringGrid2(stringGrid1); 19 | 20 | cout << stringGrid1.at(0, 1).value_or("") << endl; 21 | cout << stringGrid2.at(0, 1).value_or("") << endl; 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c12_code/08_GridInheritance/GameBoardTest.cpp: -------------------------------------------------------------------------------- 1 | #include "GameBoard.h" 2 | 3 | using namespace std; 4 | 5 | class ChessPiece 6 | { 7 | }; 8 | 9 | int main() 10 | { 11 | GameBoard chessBoard(8, 8); 12 | 13 | ChessPiece pawn; 14 | chessBoard.at(0, 0) = pawn; 15 | chessBoard.move(0, 0, 0, 1); 16 | 17 | return 0; 18 | } 19 | -------------------------------------------------------------------------------- /c12_code/09_FunctionTemplate/README.txt: -------------------------------------------------------------------------------- 1 | Include the following combinations of files in your project: 2 | 3 | 01_FindTemplate.cpp and SpreadsheetCell.cpp 4 | or 5 | 02_FindTemplateSpecialization.cpp 6 | or 7 | 03_FindTemplateOverload.cpp 8 | or 9 | 04_FindTemplateSpecialOverload.cpp 10 | -------------------------------------------------------------------------------- /c12_code/12_decltype_auto/decltype_auto.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | const std::string message = "Test"; 4 | 5 | const std::string& getString() 6 | { 7 | return message; 8 | } 9 | 10 | int main() 11 | { 12 | auto s1 = getString(); 13 | const auto& s2 = getString(); 14 | decltype(getString()) s3 = getString(); 15 | decltype(auto) s4 = getString(); 16 | } 17 | -------------------------------------------------------------------------------- /c13_code/01_OutputBasics/OutputBasics.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | int i = 7; 9 | cout << i << endl; 10 | 11 | char ch = 'a'; 12 | cout << ch << endl; 13 | 14 | string myString = "Hello World."; 15 | cout << myString << endl; 16 | 17 | 18 | int j = 11; 19 | cout << "The value of j is " << j << "!" << endl; 20 | 21 | 22 | cout << "Line 1" << endl << "Line 2" << endl << "Line 3" << endl; 23 | 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /c13_code/02_Write/Write.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | const char* test = "hello there\n"; 9 | cout.write(test, strlen(test)); 10 | 11 | return 0; 12 | } 13 | -------------------------------------------------------------------------------- /c13_code/03_Put/Put.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | cout.put('a'); 8 | 9 | return 0; 10 | } 11 | -------------------------------------------------------------------------------- /c13_code/04_Flush/flush.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | cout << "abc"; 8 | cout.flush(); // abc is written to the console. 9 | cout << "def"; 10 | cout << endl; // def is written to the console. 11 | 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c13_code/05_Exceptions/Exceptions.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | cout.exceptions(ios::failbit | ios::badbit | ios::eofbit); 9 | try { 10 | cout << "Hello World." << endl; 11 | } catch (const ios_base::failure& ex) { 12 | cerr << "Caught exception: " << ex.what() 13 | << ", error code = " << ex.code() << endl; 14 | } 15 | return 0; 16 | } 17 | -------------------------------------------------------------------------------- /c13_code/07_Input/01_string.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | string userInput; 9 | cin >> userInput; 10 | cout << "User input was " << userInput << endl; 11 | 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c13_code/07_Input/02_int.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | int userInput; 9 | cin >> userInput; 10 | cout << "User input was " << userInput << endl; 11 | 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c13_code/07_Input/03_getReservationData.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | void getReservationData() 7 | { 8 | string guestName; 9 | int partySize; 10 | cout << "Name and number of guests: "; 11 | cin >> guestName >> partySize; 12 | cout << "Thank you, " << guestName << "." << endl; 13 | if (partySize > 10) { 14 | cout << "An extra gratuity will apply." << endl; 15 | } 16 | } 17 | 18 | int main() 19 | { 20 | getReservationData(); 21 | 22 | return 0; 23 | } 24 | -------------------------------------------------------------------------------- /c13_code/07_Input/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | 3 | -------------------------------------------------------------------------------- /c13_code/12_Getline/Getline.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | const size_t kBufferSize = 1024; 8 | 9 | int main() 10 | { 11 | char buffer[kBufferSize] = { 0 }; 12 | cin.getline(buffer, kBufferSize); 13 | 14 | cout << "***" << buffer << "***" << endl; 15 | 16 | string myString; 17 | std::getline(cin, myString); 18 | 19 | cout << "***" << myString << "***" << endl; 20 | 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /c13_code/14_StringStream/StringStream.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | cout << "Enter tokens. Control+D (Unix) or Control+Z (Windows) to end." << endl; 9 | 10 | ostringstream outStream; 11 | 12 | while (cin) { 13 | string nextToken; 14 | 15 | cout << "Next token: "; 16 | cin >> nextToken; 17 | 18 | if (!cin || nextToken == "done") 19 | break; 20 | 21 | outStream << nextToken << "\t"; 22 | } 23 | 24 | cout << "The end result is: " << outStream.str(); 25 | 26 | return 0; 27 | } 28 | -------------------------------------------------------------------------------- /c13_code/15_FileStream/FileStream.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main(int argc, char* argv[]) 7 | { 8 | ofstream outFile("test.txt", ios_base::trunc); 9 | if (!outFile.good()) { 10 | cerr << "Error while opening output file!" << endl; 11 | return -1; 12 | } 13 | outFile << "There were " << argc << " arguments to this program." << endl; 14 | outFile << "They are: " << endl; 15 | for (int i = 0; i < argc; i++) { 16 | outFile << argv[i] << endl; 17 | } 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c13_code/17_tie/tie.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | ifstream inFile("input.txt"); // Note: input.txt must exist. 10 | ofstream outFile("output.txt"); 11 | // Set up a link between inFile and outFile. 12 | inFile.tie(&outFile); 13 | // Output some text to outFile. Normally, this would 14 | // not flush because std::endl is not sent. 15 | outFile << "Hello there!"; 16 | // outFile has NOT been flushed. 17 | // Read some text from inFile. This will trigger flush() 18 | // on outFile. 19 | string nextToken; 20 | inFile >> nextToken; 21 | // outFile HAS been flushed. 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c13_code/18_Bidirectional/data.txt: -------------------------------------------------------------------------------- 1 | 123 408-555-0394 2 | 124 415-555-3422 3 | 263 585-555-3490 4 | 100 650-555-3434 -------------------------------------------------------------------------------- /c14_code/01_ReadIntegerFile/02_SafeDivide.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | double SafeDivide(double num, double den) 7 | { 8 | if (den == 0) 9 | throw invalid_argument("Divide by zero"); 10 | return num / den; 11 | } 12 | 13 | int main() 14 | { 15 | try { 16 | cout << SafeDivide(5, 2) << endl; 17 | cout << SafeDivide(10, 0) << endl; 18 | cout << SafeDivide(3, 3) << endl; 19 | } 20 | catch (const invalid_argument& e) { 21 | cout << "Caught exception: " << e.what() << endl; 22 | } 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c14_code/01_ReadIntegerFile/IntegerFile.txt: -------------------------------------------------------------------------------- 1 | 3 2 | 4 3 | 5 4 | 6 -------------------------------------------------------------------------------- /c14_code/01_ReadIntegerFile/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. -------------------------------------------------------------------------------- /c14_code/02_ExceptionsAndPolymorphism/IntegerFile.txt: -------------------------------------------------------------------------------- 1 | 3 2 | 4 3 | 5 4 | 6 -------------------------------------------------------------------------------- /c14_code/02_ExceptionsAndPolymorphism/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | 3 | Notes: 4 | CathingPolymorphicallyIncorrect.cpp may generate warnings when compiled. 5 | -------------------------------------------------------------------------------- /c14_code/04_Rethrow/01_rethrow.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | void g() 7 | { 8 | throw invalid_argument("Some exception"); 9 | } 10 | 11 | void f() 12 | { 13 | try { 14 | g(); 15 | } catch (const invalid_argument& e) { 16 | cout << "caught in f: " << e.what() << endl; 17 | throw; // rethrow 18 | } 19 | } 20 | 21 | int main() 22 | { 23 | try { 24 | f(); 25 | } catch (const invalid_argument& e) { 26 | cout << "caught in main: " << e.what() << endl; 27 | } 28 | return 0; 29 | } -------------------------------------------------------------------------------- /c14_code/04_Rethrow/02_rethrow.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | void g() { throw invalid_argument("Some exception"); } 7 | 8 | void f() 9 | { 10 | try { 11 | g(); 12 | } catch (const exception& e) { 13 | cout << "caught in f: " << e.what() << endl; 14 | throw; // rethrow 15 | } 16 | } 17 | 18 | int main() 19 | { 20 | try { 21 | f(); 22 | } catch (const invalid_argument& e) { 23 | cout << "invalid_argument caught in main: " << e.what() << endl; 24 | } catch (const exception& e) { 25 | cout << "exception caught in main: " << e.what() << endl; 26 | } 27 | return 0; 28 | } 29 | -------------------------------------------------------------------------------- /c14_code/04_Rethrow/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. -------------------------------------------------------------------------------- /c14_code/05_StackUnwinding/01_BadCode.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | void funcOne(); 8 | void funcTwo(); 9 | 10 | int main() 11 | { 12 | try { 13 | funcOne(); 14 | } catch (const exception& /* e */) { 15 | cerr << "Exception caught!" << endl; 16 | return 1; 17 | } 18 | 19 | return 0; 20 | } 21 | 22 | void funcOne() 23 | { 24 | string str1; 25 | string* str2 = new string(); 26 | funcTwo(); 27 | delete str2; 28 | } 29 | 30 | void funcTwo() 31 | { 32 | ifstream fileStream; 33 | fileStream.open("filename"); 34 | throw exception(); 35 | fileStream.close(); 36 | } 37 | -------------------------------------------------------------------------------- /c14_code/05_StackUnwinding/02_SmartPointer.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | using namespace std; 7 | 8 | void funcOne(); 9 | void funcTwo(); 10 | 11 | int main() 12 | { 13 | try { 14 | funcOne(); 15 | } catch (const exception& /* e */) { 16 | cerr << "Exception caught!" << endl; 17 | return 1; 18 | } 19 | 20 | return 0; 21 | } 22 | 23 | void funcOne() 24 | { 25 | string str1; 26 | auto str2 = make_unique("hello"); 27 | funcTwo(); 28 | } 29 | 30 | void funcTwo() 31 | { 32 | ifstream fileStream; 33 | fileStream.open("filename"); 34 | throw exception(); 35 | fileStream.close(); 36 | } 37 | -------------------------------------------------------------------------------- /c14_code/05_StackUnwinding/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | 3 | -------------------------------------------------------------------------------- /c14_code/06_NewFailures/01_Exceptions.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | int* ptr = nullptr; 10 | size_t integerCount = numeric_limits::max(); 11 | cout << "Trying to allocate memory for " << integerCount << " integers." << endl; 12 | 13 | try { 14 | ptr = new int[integerCount]; 15 | } catch (const bad_alloc& e) { 16 | cerr << __FILE__ << "(" << __LINE__ << "): Unable to allocate memory: " << e.what() << endl; 17 | // Handle memory allocation failure 18 | return 1; 19 | } 20 | // Proceed with function that assumes memory has been allocated 21 | 22 | return 0; 23 | } 24 | -------------------------------------------------------------------------------- /c14_code/06_NewFailures/02_Nothrow.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | size_t integerCount = numeric_limits::max(); 10 | cout << "Trying to allocate memory for " << integerCount << " integers." << endl; 11 | 12 | int* ptr = new(nothrow) int[integerCount]; 13 | if (ptr == nullptr) { 14 | cerr << __FILE__ << "(" << __LINE__ << "): Unable to allocate memory!" << endl; 15 | // Handle memory allocation failure 16 | return 1; 17 | } 18 | // Proceed with function that assumes memory has been allocated 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c14_code/06_NewFailures/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | 3 | -------------------------------------------------------------------------------- /c14_code/07_ConstructorError/ConstructorErrorTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Matrix.h" 2 | #include "Element.h" 3 | 4 | int main() 5 | { 6 | Matrix m(10, 10); 7 | return 0; 8 | } 9 | -------------------------------------------------------------------------------- /c14_code/07_ConstructorError/Element.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | class Element 4 | { 5 | // Kept to a bare minimum, but in practice, this Element class 6 | // could throw exceptions in its constructor. 7 | private: 8 | int mValue; 9 | }; 10 | -------------------------------------------------------------------------------- /c14_code/09_GameBoard/GameBoardTest.cpp: -------------------------------------------------------------------------------- 1 | #include "GameBoard.h" 2 | 3 | void processGameBoard(const GameBoard& board) 4 | { 5 | const GamePiece& piece = board.at(0, 0); 6 | 7 | // Doesn't compile 8 | //board.at(1, 2) = piece; 9 | } 10 | 11 | int main() 12 | { 13 | GameBoard board(10, 10); 14 | GamePiece piece; 15 | 16 | board.at(0, 0) = piece; 17 | board.at(0, 1) = board.at(0, 0); 18 | 19 | GameBoard board2; 20 | board2 = board; 21 | 22 | processGameBoard(board2); 23 | 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /c14_code/09_GameBoard/NoExceptions/GameBoardTest.cpp: -------------------------------------------------------------------------------- 1 | #include "GameBoard.h" 2 | 3 | void processGameBoard(const GameBoard& board) 4 | { 5 | const GamePiece& piece = board.at(0, 0); 6 | 7 | // Doesn't compile 8 | //board.at(1, 2) = piece; 9 | } 10 | 11 | int main() 12 | { 13 | GameBoard board(10, 10); 14 | GamePiece piece; 15 | 16 | board.at(0, 0) = piece; 17 | board.at(0, 1) = board.at(0, 0); 18 | 19 | GameBoard board2; 20 | board2 = board; 21 | 22 | processGameBoard(board2); 23 | 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /c15_code/01_RelOps/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell c1(4); 9 | SpreadsheetCell c2(6); 10 | 11 | cout << (c1 == c2) << endl; 12 | cout << (c1 < c2) << endl; 13 | cout << (c1 != c2) << endl; 14 | cout << (c1 > c2) << endl; 15 | cout << (c1 <= c2) << endl; 16 | cout << (c1 >= c2) << endl; 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c15_code/02_ArithmeticOperators/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | int i, j = 4; 9 | i = -j; // unary minus 10 | i = +i; // unary plus 11 | j = +(-i); // apply unary plus to the result of applying unary minus to i 12 | j = -(-i); // apply unary minus to the result of applying unary minus to i 13 | 14 | i = i + 1; 15 | i += 1; 16 | ++i; 17 | i++; 18 | 19 | SpreadsheetCell c1(4); 20 | SpreadsheetCell c2(4); 21 | SpreadsheetCell c3 = -c1; 22 | c1++; 23 | ++c2; 24 | 25 | return 0; 26 | } 27 | -------------------------------------------------------------------------------- /c15_code/03_StreamOperators/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | int number = 10; 9 | cout << "The number is " << number << endl; 10 | string str; 11 | cin >> number >> str; 12 | 13 | SpreadsheetCell myCell, anotherCell, aThirdCell; 14 | 15 | cout << "Input 3 spreadsheetcells:" << endl; 16 | cin >> myCell >> anotherCell >> aThirdCell; 17 | cout << myCell << " " << anotherCell << " " << aThirdCell << endl; 18 | 19 | cout << "Input 3 spreadsheetcells:" << endl; 20 | operator>>(operator>>(operator>>(cin, myCell), anotherCell), aThirdCell); 21 | 22 | return 0; 23 | } 24 | -------------------------------------------------------------------------------- /c15_code/05_AssociativeArray/AssociativeArrayTest.cpp: -------------------------------------------------------------------------------- 1 | #include "AssociativeArray.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | AssociativeArray myArray; 9 | myArray["Key 1"] = 11; 10 | myArray["Key 2"] = 22; 11 | myArray["Key 3"] = 33; 12 | 13 | try { 14 | cout << myArray["Key 1"] << endl; 15 | cout << myArray["Key 2"] << endl; 16 | 17 | // Test const operator[] 18 | const AssociativeArray& c = myArray; 19 | cout << c["Key 3"] << endl; 20 | cout << c["Key 4"] << endl; 21 | } catch (const invalid_argument& ex) { 22 | cout << "Caught exception: " << ex.what() << endl; 23 | } 24 | 25 | return 0; 26 | } 27 | -------------------------------------------------------------------------------- /c15_code/07_DereferenceOps/PointerTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Pointer.h" 2 | #include "SpreadsheetCell.h" 3 | #include 4 | using namespace std; 5 | 6 | void testConst(const Pointer& p) 7 | { 8 | cout << *p; 9 | // *p = 7; 10 | } 11 | 12 | void TestConstTwo(const Pointer& /*p*/) 13 | { 14 | // p->set(5); 15 | } 16 | 17 | int main() 18 | { 19 | Pointer smartInt(new int); 20 | 21 | *smartInt = 5; // Dereference the smart pointer. 22 | cout << *smartInt << endl; 23 | 24 | Pointer smartCell(new SpreadsheetCell); 25 | 26 | smartCell->set(5); // Dereference and member select the set method. 27 | cout << smartCell->getValue() << endl; 28 | 29 | return 0; 30 | } 31 | -------------------------------------------------------------------------------- /c15_code/08_ConversionsSpreadsheetCell/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | SpreadsheetCell cell(1.23); 9 | double d1 = cell; 10 | cout << d1 << endl; 11 | string str = cell; 12 | cout << str << endl; 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c15_code/09_ExplicitConversionsSpreadsheetCell/SpreadsheetCellTest.cpp: -------------------------------------------------------------------------------- 1 | #include "SpreadsheetCell.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | // double d2 = cell + 3.3; // DOES NOT COMPILE IF YOU DEFINE operator double() 9 | 10 | // Explicit operator double() demonstration 11 | SpreadsheetCell cell = 6.6; 12 | string str = cell; 13 | double d1 = static_cast(cell); 14 | double d2 = static_cast(cell + 3.3); 15 | cout << str << endl; 16 | cout << d1 << endl; 17 | cout << d2 << endl; 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c15_code/10_ConversionsPointer/PointerTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Pointer.h" 2 | #include "SpreadsheetCell.h" 3 | 4 | #include 5 | using namespace std; 6 | 7 | void process(Pointer& p) 8 | { 9 | if (p != nullptr) { cout << "not nullptr" << endl; } 10 | if (p != NULL) { cout << "not NULL" << endl; } 11 | if (p) { cout << "not nullptr" << endl; } 12 | if (!p) { cout << "nullptr" << endl; } 13 | } 14 | 15 | int main() 16 | { 17 | Pointer smartCell(nullptr); 18 | process(smartCell); 19 | cout << endl; 20 | 21 | Pointer anotherSmartCell(new SpreadsheetCell(5.0)); 22 | process(anotherSmartCell); 23 | 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /c15_code/12_Memory/MemoryDemoTest.cpp: -------------------------------------------------------------------------------- 1 | #include "MemoryDemo.h" 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | MemoryDemo* mem = new MemoryDemo(); 8 | delete mem; 9 | 10 | mem = new MemoryDemo[10]; 11 | delete [] mem; 12 | 13 | mem = new (nothrow) MemoryDemo(); 14 | delete mem; 15 | 16 | mem = new (nothrow) MemoryDemo[10]; 17 | delete [] mem; 18 | 19 | MemoryDemo* memp = new(5) MemoryDemo(); 20 | delete memp; 21 | 22 | return 0; 23 | } 24 | -------------------------------------------------------------------------------- /c15_code/13_ExplicitDelete/ExplicitDelete.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | class MyClass 5 | { 6 | public: 7 | void* operator new(size_t size) = delete; 8 | void* operator new[](size_t size) = delete; 9 | }; 10 | 11 | int main() 12 | { 13 | // It is possible to create instances of MyClass on the stack. 14 | MyClass classOnStack; 15 | 16 | // It is not possible to create them on the heap. 17 | // The following two lines do not compile. 18 | //MyClass* p1 = new MyClass; 19 | //MyClass* pArray = new MyClass[2]; 20 | 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /c16_code/01_numeric_limits/numeric_limits.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | cout << "int:" << endl; 9 | cout << "Max int value: " << numeric_limits::max() << endl; 10 | cout << "Min int value: " << numeric_limits::min() << endl; 11 | cout << "Lowest int value: " << numeric_limits::lowest() << endl; 12 | 13 | cout << endl << "double:" << endl; 14 | cout << "Max double value: " << numeric_limits::max() << endl; 15 | cout << "Min double value: " << numeric_limits::min() << endl; 16 | cout << "Lowest double value: " << numeric_limits::lowest() << endl; 17 | 18 | return 0; 19 | } -------------------------------------------------------------------------------- /c17_code/01_TestScores/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c17_code/02_VectorCtors/01_DefaultCtor.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | vector intVector; // creates a vector of ints with zero elements 8 | return 0; 9 | } 10 | -------------------------------------------------------------------------------- /c17_code/02_VectorCtors/02_InitialElements.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | vector intVector(10, 100); // creates a vector of 10 ints with value 100 8 | return 0; 9 | } 10 | -------------------------------------------------------------------------------- /c17_code/02_VectorCtors/03_BuiltInClasses.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | vector stringVector(10, "hello"); 9 | return 0; 10 | } 11 | -------------------------------------------------------------------------------- /c17_code/02_VectorCtors/04_UserDefinedClasses.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | class Element 6 | { 7 | public: 8 | Element() {} 9 | virtual ~Element() = default; 10 | }; 11 | 12 | int main() 13 | { 14 | vector elementVector; 15 | return 0; 16 | } 17 | -------------------------------------------------------------------------------- /c17_code/02_VectorCtors/05_InitializerList.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | vector intVector({ 1, 2, 3, 4, 5, 6 }); 8 | return 0; 9 | } 10 | -------------------------------------------------------------------------------- /c17_code/02_VectorCtors/06_UniformInitialization.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | vector intVector1 = { 1, 2, 3, 4, 5, 6 }; 8 | vector intVector2{ 1, 2, 3, 4, 5, 6 }; 9 | return 0; 10 | } 11 | -------------------------------------------------------------------------------- /c17_code/02_VectorCtors/07_HeapVectorsSmartPointer.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | class Element 7 | { 8 | public: 9 | Element() {} 10 | virtual ~Element() = default; 11 | }; 12 | 13 | int main() 14 | { 15 | auto elementVector = make_unique>(10); 16 | 17 | return 0; 18 | } 19 | -------------------------------------------------------------------------------- /c17_code/02_VectorCtors/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c17_code/03_VectorCopyAssign/demo.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | using namespace std; 3 | 4 | int main() 5 | { 6 | vector intVector(10); 7 | // other code... 8 | intVector.assign(5, 100); 9 | 10 | intVector.assign({ 1, 2, 3, 4 }); 11 | 12 | vector vectorOne(10); 13 | vector vectorTwo(5, 100); 14 | 15 | vectorOne.swap(vectorTwo); 16 | // vectorOne now has 5 elements with the value 100. 17 | // vectorTwo now has 10 elements with the value 0 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c17_code/04_VectorCompare/compare.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | vector vectorOne(10); 9 | vector vectorTwo(10); 10 | 11 | if (vectorOne == vectorTwo) { 12 | cout << "equal!" << endl; 13 | } else { 14 | cout << "not equal!" << endl; 15 | } 16 | 17 | vectorOne[3] = 50; 18 | 19 | if (vectorOne < vectorTwo) { 20 | cout << "vectorOne is less than vectorTwo" << endl; 21 | } else { 22 | cout << "vectorOne is not less than vectorTwo" << endl; 23 | } 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /c17_code/05_VectorIterators/02_AccessingFields.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | vector stringVector(10, "hello"); 9 | 10 | for (auto it = begin(stringVector); it != end(stringVector); ++it) { 11 | it->append(" there"); 12 | } 13 | /* 14 | // Using Range-Based for loop 15 | for (auto& str : stringVector) { 16 | str.append(" there"); 17 | } 18 | */ 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c17_code/05_VectorIterators/03_ConstIterator.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | vector stringVector(10, "hello"); 10 | for (auto iter = cbegin(stringVector); iter != cend(stringVector); ++iter) { 11 | cout << *iter << endl; 12 | } 13 | 14 | 15 | for (const auto& element : stringVector) { 16 | cout << element << endl; 17 | } 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c17_code/05_VectorIterators/04_IteratorSafety.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | vector intVector; 8 | 9 | auto iter = end(intVector); 10 | *iter = 10; // BUG! iter doesn't refer to a valid element 11 | 12 | vector vectorOne(10); 13 | vector vectorTwo(10); 14 | 15 | // fill in the vectors 16 | 17 | // BUG! Possible infinite loop 18 | for (auto iter = begin(vectorTwo); iter != end(vectorOne); ++iter) { 19 | // loop body 20 | } 21 | 22 | return 0; 23 | } 24 | -------------------------------------------------------------------------------- /c17_code/05_VectorIterators/05_IteratorOps.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | using namespace std; 3 | 4 | int main() 5 | { 6 | vector intVector(10); 7 | 8 | auto it = begin(intVector); 9 | it += 5; 10 | --it; 11 | *it = 4; 12 | 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /c17_code/05_VectorIterators/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c17_code/06_VectorOfReferences/VectorOfReferences.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | using namespace std; 7 | 8 | int main() 9 | { 10 | string str1 = "Hello"; 11 | string str2 = "World"; 12 | 13 | // Create a vector of references to strings. 14 | vector> vec{ ref(str1) }; 15 | vec.push_back(ref(str2)); // push_back() works as well. 16 | 17 | // Modify the string referred to by the second reference in the vector. 18 | vec[1].get() += "!"; 19 | 20 | // The end result is that str2 is actually modified. 21 | cout << str1 << " " << str2 << endl; 22 | } -------------------------------------------------------------------------------- /c17_code/08_CreateVectorOfSize/CreateVectorOfSize.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | vector createVectorOfSize(size_t size) 7 | { 8 | vector vec(size); 9 | int contents = 0; 10 | for (auto& i : vec) { 11 | i = contents++; 12 | } 13 | return vec; 14 | } 15 | 16 | int main() 17 | { 18 | vector myVector; 19 | myVector = createVectorOfSize(123); 20 | 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /c17_code/09_MovePushBack/MovePushBack.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | vector vec; 9 | 10 | // push_back will trigger copying 11 | string myElement(5, 'a'); // Constructs the string "aaaaa" 12 | vec.push_back(myElement); 13 | 14 | // no copying, due to move semantics 15 | vec.push_back(move(myElement)); 16 | vec.push_back(string(5, 'a')); 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c17_code/10_Emplace/Emplace.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | vector vec; 9 | 10 | vec.emplace_back(5, 'a'); 11 | 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c17_code/13_StudentEnrollment/course1.txt: -------------------------------------------------------------------------------- 1 | Washington, George 2 | Jefferson, Thomas 3 | Clinton, Bill 4 | -------------------------------------------------------------------------------- /c17_code/13_StudentEnrollment/course2.txt: -------------------------------------------------------------------------------- 1 | Bush, George W 2 | Carter, Jimmy 3 | Clinton, Bill 4 | -------------------------------------------------------------------------------- /c17_code/13_StudentEnrollment/course3.txt: -------------------------------------------------------------------------------- 1 | Lincoln, Abraham 2 | Clinton, Bill 3 | -------------------------------------------------------------------------------- /c17_code/13_StudentEnrollment/dropped.txt: -------------------------------------------------------------------------------- 1 | Bush, George W 2 | Lincoln, Abraham 3 | -------------------------------------------------------------------------------- /c17_code/15_std_array/02_get.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | array myArray{ 11, 22, 33 }; 9 | cout << std::get<1>(myArray) << endl; 10 | // cout << std::get<10>(myArray) << endl; // Compilation error! 11 | } -------------------------------------------------------------------------------- /c17_code/15_std_array/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c17_code/17_ErrorCorrelatorPqueue/ErrorCorrelatorTest.cpp: -------------------------------------------------------------------------------- 1 | #include "ErrorCorrelator.h" 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | ErrorCorrelator ec; 10 | 11 | ec.addError(Error(3, "Unable to read file")); 12 | ec.addError(Error(1, "Incorrect entry from user")); 13 | ec.addError(Error(10, "Unable to allocate memory!")); 14 | 15 | while (true) { 16 | try { 17 | Error e = ec.getError(); 18 | cout << e << endl; 19 | } catch (const out_of_range&) { 20 | cout << "Finished processing errors" << endl; 21 | break; 22 | } 23 | } 24 | 25 | return 0; 26 | } 27 | -------------------------------------------------------------------------------- /c17_code/18_ErrorCorrelatorStack/ErrorCorrelatorTest.cpp: -------------------------------------------------------------------------------- 1 | #include "ErrorCorrelator.h" 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | ErrorCorrelator ec; 10 | 11 | ec.addError(Error(3, "Unable to read file")); 12 | ec.addError(Error(1, "Incorrect entry from user")); 13 | ec.addError(Error(10, "Unable to allocate memory!")); 14 | 15 | while (true) { 16 | try { 17 | Error e = ec.getError(); 18 | cout << e << endl; 19 | } catch (const out_of_range&) { 20 | cout << "Finished processing errors" << endl; 21 | break; 22 | } 23 | } 24 | 25 | return 0; 26 | } 27 | -------------------------------------------------------------------------------- /c17_code/19_Pair/README.txt: -------------------------------------------------------------------------------- 1 | Visual C++ 2017 does not support template parameter deduction for constructors yet. -------------------------------------------------------------------------------- /c17_code/20_MapBasics/01_Map.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | class Data final 6 | { 7 | public: 8 | explicit Data(int value = 0) : mValue(value) { } 9 | int getValue() const { return mValue; } 10 | void setValue(int value) { mValue = value; } 11 | 12 | private: 13 | int mValue; 14 | }; 15 | 16 | int main() 17 | { 18 | map dataMap; 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c17_code/20_MapBasics/02_MapUniformInit.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | map m = { 10 | { "Marc G.", 123 }, 11 | { "Warren B.", 456 }, 12 | { "Peter V.W.", 789 } 13 | }; 14 | 15 | for (const auto& p : m) { 16 | cout << p.first << " = " << p.second << endl; 17 | } 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c17_code/20_MapBasics/04_MapIndexOperator.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | class Data final 7 | { 8 | public: 9 | explicit Data(int value = 0) : mValue(value) { } 10 | int getValue() const { return mValue; } 11 | void setValue(int value) { mValue = value; } 12 | 13 | private: 14 | int mValue; 15 | }; 16 | 17 | int main() 18 | { 19 | map dataMap; 20 | dataMap[1] = Data(4); 21 | dataMap[1] = Data(6); // Replaces the element with key 1 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c17_code/20_MapBasics/05_MapAsParameter.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | void func(const map& m) 7 | { 8 | // cout << m[1] << endl; // Error 9 | } 10 | 11 | int main() 12 | { 13 | map m; 14 | m[1] = 11; 15 | m[2] = 22; 16 | m[3] = 33; 17 | func(m); 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c17_code/20_MapBasics/07_MapLookup.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | class Data final 6 | { 7 | public: 8 | explicit Data(int value = 0) : mValue(value) { } 9 | int getValue() const { return mValue; } 10 | void setValue(int value) { mValue = value; } 11 | 12 | private: 13 | int mValue; 14 | }; 15 | 16 | int main() 17 | { 18 | map dataMap; 19 | dataMap[1] = Data(4); 20 | dataMap[1] = Data(6); 21 | dataMap[1].setValue(100); 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c17_code/20_MapBasics/08_MapFind.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | class Data final 7 | { 8 | public: 9 | explicit Data(int value = 0) : mValue(value) { } 10 | int getValue() const { return mValue; } 11 | void setValue(int value) { mValue = value; } 12 | 13 | private: 14 | int mValue; 15 | }; 16 | 17 | int main() 18 | { 19 | map dataMap; 20 | dataMap[1] = Data(4); 21 | dataMap[1] = Data(6); 22 | 23 | auto it = dataMap.find(1); 24 | // If your compiler does not support the C++11 auto keyword: 25 | //map::iterator it = dataMap.find(1); 26 | if (it != end(dataMap)) { 27 | it->second.setValue(100); 28 | } 29 | 30 | return 0; 31 | } 32 | -------------------------------------------------------------------------------- /c17_code/20_MapBasics/09_MapErase.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | class Data final 7 | { 8 | public: 9 | explicit Data(int value = 0) : mValue(value) { } 10 | int getValue() const { return mValue; } 11 | void setValue(int value) { mValue = value; } 12 | 13 | private: 14 | int mValue; 15 | }; 16 | 17 | int main() 18 | { 19 | map dataMap; 20 | dataMap[1] = Data(4); 21 | 22 | cout << "There are " << dataMap.count(1) << " elements with key 1" << endl; 23 | dataMap.erase(1); 24 | cout << "There are " << dataMap.count(1) << " elements with key 1" << endl; 25 | 26 | return 0; 27 | } 28 | -------------------------------------------------------------------------------- /c17_code/20_MapBasics/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. -------------------------------------------------------------------------------- /c17_code/21_Nodes/01_ExtractAndInsert.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | class Data final 6 | { 7 | public: 8 | explicit Data(int value = 0) : mValue(value) { } 9 | int getValue() const { return mValue; } 10 | void setValue(int value) { mValue = value; } 11 | 12 | private: 13 | int mValue; 14 | }; 15 | 16 | int main() 17 | { 18 | map dataMap; 19 | dataMap[1] = Data(4); 20 | 21 | map dataMap2; 22 | dataMap2.insert(dataMap.extract(1)); 23 | 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /c17_code/21_Nodes/02_merge.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | map src = { { 1, 11 },{ 2, 22 } }; 8 | map dst = { { 2, 22 },{ 3, 33 },{ 4, 44 },{ 5, 55 } }; 9 | dst.merge(src); 10 | 11 | return 0; 12 | } 13 | -------------------------------------------------------------------------------- /c17_code/21_Nodes/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. -------------------------------------------------------------------------------- /c17_code/22_BankAccount/BankDBTest.cpp: -------------------------------------------------------------------------------- 1 | #include "BankDB.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | BankDB db; 9 | 10 | db.addAccount(BankAccount(100, "Nicholas Solter")); 11 | db.addAccount(BankAccount(200, "Scott Kleper")); 12 | 13 | try { 14 | auto& acct = db.findAccount(100); 15 | cout << "Found account 100" << endl; 16 | acct.setClientName("Nicholas A Solter"); 17 | 18 | auto& acct2 = db.findAccount("Scott Kleper"); 19 | cout << "Found account of Scott Kleper" << endl; 20 | 21 | auto& acct3 = db.findAccount(1000); 22 | } catch (const out_of_range& caughtException) { 23 | cout << "Unable to find account: " << caughtException.what() << endl; 24 | } 25 | 26 | return 0; 27 | } 28 | -------------------------------------------------------------------------------- /c17_code/23_BuddyList/BuddyList.cpp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/HodongMan/professional-cpp-4th-ed/301d835f3a7df790e4873bcf8c797f5711b4d932/c17_code/23_BuddyList/BuddyList.cpp -------------------------------------------------------------------------------- /c17_code/24_AccessControlList/AccessList.cpp: -------------------------------------------------------------------------------- 1 | #include "AccessList.h" 2 | 3 | using namespace std; 4 | 5 | AccessList::AccessList(initializer_list initlist) 6 | { 7 | mAllowed.insert(begin(initlist), end(initlist)); 8 | } 9 | 10 | void AccessList::addUser(string_view user) 11 | { 12 | mAllowed.emplace(user); 13 | } 14 | 15 | void AccessList::removeUser(string_view user) 16 | { 17 | mAllowed.erase(string(user)); 18 | } 19 | 20 | bool AccessList::isAllowed(string_view user) const 21 | { 22 | return (mAllowed.count(string(user)) != 0); 23 | } 24 | 25 | vector AccessList::getAllUsers() const 26 | { 27 | return { begin(mAllowed), end(mAllowed) }; 28 | } 29 | -------------------------------------------------------------------------------- /c17_code/24_AccessControlList/AccessListTest.cpp: -------------------------------------------------------------------------------- 1 | #include "AccessList.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | AccessList fileX = { "pvw", "mgregoire", "baduser" }; 9 | fileX.removeUser("baduser"); 10 | 11 | if (fileX.isAllowed("mgregoire")) { 12 | cout << "mgregoire has permissions" << endl; 13 | } 14 | 15 | if (fileX.isAllowed("baduser")) { 16 | cout << "baduser has permissions" << endl; 17 | } 18 | 19 | auto users = fileX.getAllUsers(); 20 | for (const auto& user : users) { 21 | cout << user << " "; 22 | } 23 | cout << endl; 24 | 25 | return 0; 26 | } 27 | -------------------------------------------------------------------------------- /c17_code/26_unordered_map/unordered_map.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | unordered_map m = { 10 | {1, "Item 1"}, 11 | {2, "Item 2"}, 12 | {3, "Item 3"}, 13 | {4, "Item 4"}, 14 | }; 15 | 16 | // Using C++17 structured bindings. 17 | for (const auto&[key, value] : m) { 18 | cout << key << " = " << value << endl; 19 | } 20 | 21 | // Without structured bindings. 22 | for (const auto& p : m) { 23 | cout << p.first << " = " << p.second << endl; 24 | } 25 | 26 | return 0; 27 | } 28 | -------------------------------------------------------------------------------- /c17_code/29_StringContainers/StringExample.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | string myString; 9 | 10 | myString.insert(cend(myString), 'h'); 11 | myString.insert(cend(myString), 'e'); 12 | myString.push_back('l'); 13 | myString.push_back('l'); 14 | myString.push_back('o'); 15 | 16 | for (const auto& letter : myString) { 17 | cout << letter; 18 | } 19 | cout << endl; 20 | 21 | for (auto it = cbegin(myString); it != cend(myString); ++it) { 22 | cout << *it; 23 | } 24 | cout << endl; 25 | 26 | return 0; 27 | } 28 | -------------------------------------------------------------------------------- /c17_code/30_BitsetBasics/01_BitsetBasics.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | bitset<10> myBitset; 9 | 10 | myBitset.set(3); 11 | myBitset.set(6); 12 | myBitset[8] = true; 13 | myBitset[9] = myBitset[3]; 14 | 15 | if (myBitset.test(3)) { 16 | cout << "Bit 3 is set!" << endl; 17 | } 18 | cout << myBitset << endl; 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c17_code/30_BitsetBasics/02_BitwiseOperators.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | auto str1 = "0011001100"; 8 | auto str2 = "0000111100"; 9 | bitset<10> bitsOne(str1); 10 | bitset<10> bitsTwo(str2); 11 | 12 | auto bitsThree = bitsOne & bitsTwo; 13 | cout << bitsThree << endl; 14 | bitsThree <<= 4; 15 | cout << bitsThree << endl; 16 | 17 | return 0; 18 | } 19 | -------------------------------------------------------------------------------- /c17_code/30_BitsetBasics/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c17_code/31_CableCompany/CableCompanyTest.cpp: -------------------------------------------------------------------------------- 1 | #include "CableCompany.h" 2 | #include 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | CableCompany myCC; 8 | auto basic_pkg = "1111000000"; 9 | auto premium_pkg = "1111111111"; 10 | auto sports_pkg = "0000100111"; 11 | 12 | myCC.addPackage("basic", bitset(basic_pkg)); 13 | myCC.addPackage("premium", bitset(premium_pkg)); 14 | myCC.addPackage("sports", bitset(sports_pkg)); 15 | 16 | myCC.newCustomer("Marc G.", "basic"); 17 | myCC.addPackageToCustomer("Marc G.", "sports"); 18 | cout << myCC.getCustomerChannels("Marc G.") << endl; 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c18_code/01_AlgorithmOverview/03_FindIfLambda.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | int num; 10 | 11 | vector myVector; 12 | while (true) { 13 | cout << "Enter a test score to add (0 to stop): "; 14 | cin >> num; 15 | if (num == 0) { 16 | break; 17 | } 18 | myVector.push_back(num); 19 | } 20 | 21 | auto endIt = cend(myVector); 22 | auto it = find_if(cbegin(myVector), endIt, [](int i){ return i >= 100; }); 23 | if (it == endIt) { 24 | cout << "No perfect scores" << endl; 25 | } else { 26 | cout << "Found a \"perfect\" score of " << *it << endl; 27 | } 28 | return 0; 29 | } 30 | -------------------------------------------------------------------------------- /c18_code/01_AlgorithmOverview/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c18_code/02_Function/01_function.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | void func(int num, const string& str) 8 | { 9 | cout << "func(" << num << ", " << str << ")" << endl; 10 | } 11 | 12 | int main() 13 | { 14 | function f1 = func; 15 | //auto f1 = func; 16 | f1(1, "test"); 17 | 18 | return 0; 19 | } 20 | 21 | -------------------------------------------------------------------------------- /c18_code/02_Function/02_function_find_if.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | using namespace std; 7 | 8 | bool isEven(int num) 9 | { 10 | return num % 2 == 0; 11 | } 12 | 13 | int main() 14 | { 15 | vector vec{ 1,2,3,4,5,6,7,8,9 }; 16 | 17 | function fcn = isEven; 18 | auto result = find_if(cbegin(vec), cend(vec), fcn); 19 | if (result != cend(vec)) { 20 | cout << "First even number: " << *result << endl; 21 | } else { 22 | cout << "No even number found." << endl; 23 | } 24 | 25 | return 0; 26 | } 27 | 28 | -------------------------------------------------------------------------------- /c18_code/02_Function/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c18_code/03_Lambdas/03_GenericCapture.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | { 9 | double pi = 3.1415; 10 | auto myLambda = [myCapture = "Pi: ", pi]{ cout << myCapture << pi; }; 11 | myLambda(); 12 | } 13 | 14 | cout << endl; 15 | 16 | { 17 | auto myPtr = std::make_unique(3.1415); 18 | auto myLambda = [p = std::move(myPtr)]{ cout << *p; }; 19 | myLambda(); 20 | } 21 | 22 | cout << endl; 23 | 24 | { 25 | auto myPtr = std::make_unique(3.1415); 26 | auto myLambda = [myPtr = std::move(myPtr)]{ cout << *myPtr; }; 27 | myLambda(); 28 | } 29 | 30 | cout << endl; 31 | 32 | return 0; 33 | } 34 | -------------------------------------------------------------------------------- /c18_code/03_Lambdas/04_multiplyBy2Lambda.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | function multiplyBy2Lambda(int x) 7 | { 8 | return [x]{ return 2 * x; }; 9 | } 10 | 11 | // Using function return type deduction 12 | //auto multiplyBy2Lambda(int x) 13 | //{ 14 | // return [x]{ return 2 * x; }; 15 | //} 16 | 17 | int main() 18 | { 19 | //function fn = multiplyBy2Lambda(5); 20 | //cout << fn() << endl; 21 | 22 | auto fn = multiplyBy2Lambda(5); 23 | cout << fn() << endl; 24 | 25 | 26 | return 0; 27 | } -------------------------------------------------------------------------------- /c18_code/03_Lambdas/05_count_if.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | vector vec{ 1, 2, 3, 4, 5, 6, 7, 8, 9 }; 10 | int value = 3; 11 | int cnt = count_if(cbegin(vec), cend(vec), 12 | [value](int i){ return i > value; }); 13 | cout << "Found " << cnt << " values > " << value << endl; 14 | 15 | return 0; 16 | } -------------------------------------------------------------------------------- /c18_code/03_Lambdas/06_count_if_ref.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | vector vec = { 1, 2, 3, 4, 5, 6, 7, 8, 9 }; 10 | int value = 3; 11 | int cntLambdaCalled = 0; 12 | int cnt = count_if(cbegin(vec), cend(vec), 13 | [value, &cntLambdaCalled](int i){ ++cntLambdaCalled; return i > value; }); 14 | cout << "The lambda expression was called " << cntLambdaCalled 15 | << " times." << endl; 16 | cout << "Found " << cnt << " values > " << value << endl; 17 | 18 | return 0; 19 | } -------------------------------------------------------------------------------- /c18_code/03_Lambdas/07_generate.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | vector vec(10); 10 | int value = 1; 11 | generate(begin(vec), end(vec), [&value]{ value *= 2; return value; }); 12 | for (const auto& i : vec) { 13 | cout << i << " "; 14 | } 15 | cout << endl; 16 | 17 | return 0; 18 | } 19 | -------------------------------------------------------------------------------- /c18_code/03_Lambdas/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c18_code/04_FunctionObjects/02_QueueLess.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | priority_queue myQueue; 9 | 10 | myQueue.push(3); 11 | myQueue.push(4); 12 | myQueue.push(2); 13 | myQueue.push(1); 14 | 15 | while (!myQueue.empty()) { 16 | cout << myQueue.top() << " "; 17 | myQueue.pop(); 18 | } 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c18_code/04_FunctionObjects/03_QueueGreater.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | priority_queue, greater<>> myQueue; // C++14 transparent function object 9 | //priority_queue, greater> myQueue; // Pre-C++14 10 | 11 | myQueue.push(3); 12 | myQueue.push(4); 13 | myQueue.push(2); 14 | myQueue.push(1); 15 | 16 | while (!myQueue.empty()) { 17 | cout << myQueue.top() << " "; 18 | myQueue.pop(); 19 | } 20 | 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /c18_code/04_FunctionObjects/05_bind.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | using namespace std; 7 | 8 | void func(int num, string_view str) 9 | { 10 | cout << "func(" << num << ", " << str << ")" << endl; 11 | } 12 | 13 | int main() 14 | { 15 | // Bind second argument to a fixed value. 16 | string myString = "abc"; 17 | auto f1 = bind(func, placeholders::_1, myString); 18 | f1(16); 19 | 20 | // Rearrange arguments 21 | auto f2 = bind(func, placeholders::_2, placeholders::_1); 22 | f2("Test", 32); 23 | 24 | return 0; 25 | } 26 | 27 | -------------------------------------------------------------------------------- /c18_code/04_FunctionObjects/06_Ref.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | using namespace std; 7 | 8 | void increment(int& value) 9 | { 10 | ++value; 11 | } 12 | 13 | int main() 14 | { 15 | int index = 0; 16 | increment(index); 17 | 18 | auto incr1 = bind(increment, index); 19 | incr1(); 20 | 21 | auto incr2 = bind(increment, ref(index)); 22 | incr2(); 23 | 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /c18_code/04_FunctionObjects/07_BindWithOverloads.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | void overloaded(int /* num */) {} 6 | void overloaded(float /* f */) {} 7 | 8 | int main() 9 | { 10 | // Bind overloaded function 11 | //auto f3 = bind(overloaded, placeholders::_1); // ERROR 12 | auto f4 = bind((void(*)(float))overloaded, placeholders::_1); // OK 13 | 14 | return 0; 15 | } 16 | 17 | -------------------------------------------------------------------------------- /c18_code/04_FunctionObjects/12_Invokers.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | using namespace std; 7 | 8 | void printMessage(string_view message) 9 | { 10 | cout << message << endl; 11 | } 12 | 13 | int main() 14 | { 15 | invoke(printMessage, "Hello invoke."); 16 | invoke([](const auto& msg) { cout << msg << endl; }, "Hello invoke."); 17 | string msg = "Hello invoke."; 18 | cout << invoke(&string::size, msg) << endl; 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c18_code/04_FunctionObjects/13_WritingFunctionObject.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | 7 | using namespace std; 8 | 9 | class myIsDigit 10 | { 11 | public: 12 | bool operator()(char c) const { return ::isdigit(c) != 0; } 13 | }; 14 | 15 | bool isNumber(string_view str) 16 | { 17 | auto endIter = end(str); 18 | auto it = find_if(begin(str), endIter, not_fn(myIsDigit())); 19 | return (it == endIter); 20 | } 21 | 22 | int main() 23 | { 24 | cout << isNumber("12345") << endl; 25 | cout << isNumber("hello") << endl; 26 | cout << isNumber("1234a") << endl; 27 | 28 | return 0; 29 | } 30 | -------------------------------------------------------------------------------- /c18_code/04_FunctionObjects/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. -------------------------------------------------------------------------------- /c18_code/05_NonModifyingAlgorithms/02_BoyerMoore.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | // C++17 Boyer-Moore searcher 10 | string text = "This is the haystack to search a needle in."; 11 | string toSearchFor = "needle"; 12 | auto searcher = std::boyer_moore_searcher(cbegin(toSearchFor), cend(toSearchFor)); 13 | auto result = search(cbegin(text), cend(text), searcher); 14 | if (result != cend(text)) { 15 | cout << "Found the needle." << endl; 16 | } else { 17 | cout << "Needle not found." << endl; 18 | } 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c18_code/05_NonModifyingAlgorithms/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | 3 | Visual C++ 2017 does not yet properly support Boyer Moore searchers. -------------------------------------------------------------------------------- /c18_code/06_ModifyingAlgorithms/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c18_code/07_OperationalAlgorithms/01_ForEachBasicLambda.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | map myMap = { { 4, 40 }, { 5, 50 }, { 6, 60 } }; 10 | for_each(cbegin(myMap), cend(myMap), [](const auto& p) 11 | { cout << p.first << "->" << p.second << endl; }); 12 | 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /c18_code/07_OperationalAlgorithms/04_ForEachN.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | map myMap = { { 4, 40 }, { 5, 50 }, { 6, 60 } }; 10 | for_each_n(cbegin(myMap), 2, [](const auto& p) 11 | { cout << p.first << "->" << p.second << endl; }); 12 | 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /c18_code/07_OperationalAlgorithms/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. -------------------------------------------------------------------------------- /c18_code/08_SwapAndExchangeAlgorithms/01_swap.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | int a = 11; 9 | int b = 22; 10 | 11 | cout << "Before swap(): a = " << a << ", b = " << b << endl; 12 | 13 | swap(a, b); 14 | 15 | cout << "After swap(): a = " << a << ", b = " << b << endl; 16 | 17 | return 0; 18 | } -------------------------------------------------------------------------------- /c18_code/08_SwapAndExchangeAlgorithms/02_exchange.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | int a = 11; 9 | int b = 22; 10 | 11 | cout << "Before exchange(): a = " << a << ", b = " << b << endl; 12 | 13 | int returnedValue = exchange(a, b); 14 | 15 | cout << "After exchange(): a = " << a << ", b = " << b << endl; 16 | cout << "exchange() returned: " << returnedValue << endl; 17 | 18 | return 0; 19 | } -------------------------------------------------------------------------------- /c18_code/08_SwapAndExchangeAlgorithms/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. -------------------------------------------------------------------------------- /c18_code/09_PartitionAlgorithms/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c18_code/11_BinarySearchAlgorithms/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. -------------------------------------------------------------------------------- /c18_code/12_SetAlgorithms/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c18_code/13_MinMaxAlgorithms/02_clamp.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | cout << clamp(-3, 1, 10) << endl; 9 | cout << clamp(3, 1, 10) << endl; 10 | cout << clamp(22, 1, 10) << endl; 11 | 12 | return 0; 13 | } 14 | -------------------------------------------------------------------------------- /c18_code/13_MinMaxAlgorithms/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c18_code/15_NumericalAlgorithms/01_inner_product.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | vector v1{ 1, 2, 3, 4 }; 10 | vector v2{ 9, 8, 7, 6 }; 11 | cout << inner_product(cbegin(v1), cend(v1), cbegin(v2), 0) << endl; 12 | 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /c18_code/15_NumericalAlgorithms/02_iota.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | vector vec(10); 10 | iota(begin(vec), end(vec), 5); 11 | for (auto& i : vec) { cout << i << " "; } 12 | cout << endl; 13 | 14 | return 0; 15 | } -------------------------------------------------------------------------------- /c18_code/15_NumericalAlgorithms/03_reduce.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | vector vec{ 1,3,6,4,6,9 }; 10 | double result1 = std::accumulate(cbegin(vec), cend(vec), 0.0); 11 | double result2 = std::reduce(std::execution::par_unseq, cbegin(vec), cend(vec)); 12 | 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /c18_code/15_NumericalAlgorithms/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c19_code/01_WideStrings/wcout.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | wcout << L"I am a wide-character string literal." << endl; 8 | 9 | return 0; 10 | } 11 | -------------------------------------------------------------------------------- /c19_code/02_CharTypes/CharTypes.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | const char* s1 = u8R"(Raw UTF-8 encoded string literal)"; 8 | const wchar_t* s2 = LR"(Raw wide string literal)"; 9 | const char16_t* s3 = uR"(Raw char16_t string literal)"; 10 | const char32_t* s4 = UR"(Raw char32_t string literal)"; 11 | 12 | cout << s1 << endl; 13 | wcout << s2 << endl; 14 | // Can't stream s3 and s4, because streams don't support char16_t and char32_t. 15 | 16 | const char* formula = u8"\u03C0 r\u00B2"; 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c19_code/03_Imbue/Imbue.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | // User locale 9 | wcout.imbue(locale("")); 10 | wcout << 32767 << endl; 11 | 12 | // Classic/neutral locale 13 | wcout.imbue(locale("C")); 14 | wcout << 32767 << endl; 15 | 16 | // U.S. English locale 17 | wcout.imbue(locale("en-US")); // "en_US" for POSIX 18 | wcout << 32767 << endl; 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c19_code/04_Locales/Locales.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | locale loc(""); 10 | 11 | if (loc.name().find("en_US") == string::npos && 12 | loc.name().find("en-US") == string::npos) { 13 | wcout << L"Welcome non-U.S. English speaker!" << endl; 14 | } else { 15 | wcout << L"Welcome U.S. English speaker!" << endl; 16 | } 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c19_code/05_Facets/use_facet.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | locale locUSEng("en-US"); // For Windows 9 | //locale locUSEng("en_US"); // For Linux 10 | locale locBritEng("en-GB"); // For Windows 11 | //locale locBritEng("en_GB"); // For Linux 12 | 13 | wstring dollars = use_facet>(locUSEng).curr_symbol(); 14 | wstring pounds = use_facet>(locBritEng).curr_symbol(); 15 | 16 | wcout << L"In the US, the currency symbol is " << dollars << endl; 17 | wcout << L"In Great Britain, the currency symbol is " << pounds << endl; 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c19_code/06_RegularExpressions/01_regex_match_dates_1.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | regex r("\\d{4}/(?:0?[1-9]|1[0-2])/(?:0?[1-9]|[1-2][0-9]|3[0-1])"); 10 | while (true) { 11 | cout << "Enter a date (year/month/day) (q=quit): "; 12 | string str; 13 | if (!getline(cin, str) || str == "q") 14 | break; 15 | 16 | if (regex_match(str, r)) 17 | cout << " Valid date." << endl; 18 | else 19 | cout << " Invalid date!" << endl; 20 | } 21 | 22 | return 0; 23 | } 24 | -------------------------------------------------------------------------------- /c19_code/06_RegularExpressions/03_regex_search_comments.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | regex r("//\\s*(.+)$"); 10 | while (true) { 11 | cout << "Enter a string with optional code comments (q=quit): "; 12 | string str; 13 | if (!getline(cin, str) || str == "q") 14 | break; 15 | 16 | smatch m; 17 | if (regex_search(str, m, r)) 18 | cout << " Found comment '" << m[1] << "'" << endl; 19 | else 20 | cout << " No comment found!" << endl; 21 | } 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c19_code/06_RegularExpressions/04_regex_iterator.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | regex reg("[\\w]+"); 10 | while (true) { 11 | cout << "Enter a string to split (q=quit): "; 12 | string str; 13 | if (!getline(cin, str) || str == "q") 14 | break; 15 | 16 | const sregex_iterator end; 17 | for (sregex_iterator iter(cbegin(str), cend(str), reg); iter != end; ++iter) { 18 | cout << "\"" << (*iter)[0] << "\"" << endl; 19 | } 20 | } 21 | 22 | return 0; 23 | } -------------------------------------------------------------------------------- /c19_code/06_RegularExpressions/05_regex_token_iterator_1.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | regex reg("[\\w]+"); 10 | while (true) { 11 | cout << "Enter a string to split (q=quit): "; 12 | string str; 13 | if (!getline(cin, str) || str == "q") 14 | break; 15 | 16 | const sregex_token_iterator end; 17 | for (sregex_token_iterator iter(cbegin(str), cend(str), reg); 18 | iter != end; ++iter) { 19 | cout << "\"" << *iter << "\"" << endl; 20 | } 21 | } 22 | 23 | return 0; 24 | } -------------------------------------------------------------------------------- /c19_code/06_RegularExpressions/06_regex_token_iterator_2.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | using namespace std; 7 | 8 | int main() 9 | { 10 | regex reg("^(\\d{4})/(0?[1-9]|1[0-2])/(0?[1-9]|[1-2][0-9]|3[0-1])$"); 11 | while (true) { 12 | cout << "Enter a date (year/month/day) (q=quit): "; 13 | string str; 14 | if (!getline(cin, str) || str == "q") 15 | break; 16 | 17 | vector indices{ 2, 3 }; 18 | const sregex_token_iterator end; 19 | for (sregex_token_iterator iter(cbegin(str), cend(str), reg, indices); 20 | iter != end; ++iter) { 21 | cout << "\"" << *iter << "\"" << endl; 22 | } 23 | } 24 | 25 | return 0; 26 | } -------------------------------------------------------------------------------- /c19_code/06_RegularExpressions/07_regex_token_iterator_field_splitting.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | regex reg(R"(\s*[,;]\s*)"); 10 | while (true) { 11 | cout << "Enter a string to split on ',' and ';' (q=quit): "; 12 | string str; 13 | if (!getline(cin, str) || str == "q") 14 | break; 15 | 16 | const sregex_token_iterator end; 17 | for (sregex_token_iterator iter(cbegin(str), cend(str), reg, -1); 18 | iter != end; ++iter) { 19 | cout << "\"" << *iter << "\"" << endl; 20 | } 21 | } 22 | 23 | return 0; 24 | } -------------------------------------------------------------------------------- /c19_code/06_RegularExpressions/08_regex_replace_1.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | const string str("

Header

Some text

"); 10 | regex r("

(.*)

(.*)

"); 11 | 12 | const string format("H1=$1 and P=$2"); 13 | string result = regex_replace(str, r, format); 14 | 15 | cout << "Original string: '" << str << "'" << endl; 16 | cout << "New string : '" << result << "'" << endl; 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c19_code/06_RegularExpressions/08_regex_replace_2.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | const string str("

Header

Some text

"); 10 | regex r("

(.*)

(.*)

"); 11 | 12 | const string format("H1=$1 and P=$2"); 13 | string result = regex_replace(str, r, format, regex_constants::format_no_copy); 14 | 15 | cout << "Original string: '" << str << "'" << endl; 16 | cout << "New string : '" << result << "'" << endl; 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c19_code/06_RegularExpressions/10_regex_replace_3.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | regex reg("([\\w]+)"); 10 | const string format("$1\n"); 11 | while (true) { 12 | cout << "Enter a string to split over multiple lines (q=quit): "; 13 | string str; 14 | if (!getline(cin, str) || str == "q") 15 | break; 16 | 17 | cout << regex_replace(str, reg, format, regex_constants::format_no_copy) << endl; 18 | } 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c19_code/06_RegularExpressions/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | 3 | -------------------------------------------------------------------------------- /c20_code/02_Chrono/05_time_point.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | using namespace std::chrono; 6 | 7 | int main() 8 | { 9 | // Create a time_point representing the epoch 10 | // of the associated steady clock 11 | time_point tp1; 12 | // or 13 | // steady_clock::time_point tp1; 14 | 15 | // Add 10 minutes to the time_point 16 | tp1 += minutes(10); 17 | // Store the duration between epoch and time_point 18 | auto d1 = tp1.time_since_epoch(); 19 | // Convert the duration to seconds and output to the console 20 | duration d2(d1); 21 | cout << d2.count() << " seconds" << endl; 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c20_code/02_Chrono/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c20_code/03_Random/01_old.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int getRandom(int min, int max) 7 | { 8 | return (rand() % static_cast(max + 1 - min)) + min; 9 | } 10 | 11 | int main() 12 | { 13 | srand(static_cast(time(nullptr))); 14 | 15 | cout << rand() << endl; 16 | 17 | cout << getRandom(1, 6) << endl; 18 | 19 | return 0; 20 | } 21 | 22 | -------------------------------------------------------------------------------- /c20_code/03_Random/02_random_device.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | random_device rnd; 9 | cout << "Entropy: " << rnd.entropy() << endl; 10 | cout << "Min value: " << rnd.min() 11 | << ", Max value: " << rnd.max() << endl; 12 | cout << "Random number: " << rnd() << endl; 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c20_code/03_Random/03_basic.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | random_device seeder; 10 | const auto seed = seeder.entropy() ? seeder() : time(nullptr); 11 | mt19937 eng(static_cast(seed)); 12 | 13 | uniform_int_distribution dist(1, 99); 14 | cout << dist(eng) << endl; 15 | 16 | return 0; 17 | } 18 | 19 | -------------------------------------------------------------------------------- /c20_code/03_Random/04_generate.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | using namespace std; 9 | 10 | int main() 11 | { 12 | random_device seeder; 13 | const auto seed = seeder.entropy() ? seeder() : time(nullptr); 14 | mt19937 eng(static_cast(seed)); 15 | uniform_int_distribution dist(1, 99); 16 | 17 | auto gen = std::bind(dist, eng); 18 | 19 | vector vec(10); 20 | generate(begin(vec), end(vec), gen); 21 | 22 | for (auto i : vec) { 23 | cout << i << " "; 24 | } 25 | cout << endl; 26 | 27 | return 0; 28 | } 29 | 30 | -------------------------------------------------------------------------------- /c20_code/03_Random/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c20_code/07_Tuple/01_pair.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | pair p1(16, "Hello World"); 10 | pair p2(true, 0.123f); 11 | cout << "p1 = (" << p1.first << ", " << p1.second << ")" << endl; 12 | cout << "p2 = (" << p2.first << ", " << p2.second << ")" << endl; 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c20_code/07_Tuple/03_structured_bindings.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | tuple t1(16, "Test", true); 10 | //tuple t1(16, "Test"s, true); // C++17 template argument deduction for constructors 11 | auto[i, str, b] = t1; 12 | cout << "Decomposed: i = " << i << ", str = \"" << str << "\", b = " << b << endl; 13 | 14 | 15 | return 0; 16 | } -------------------------------------------------------------------------------- /c20_code/07_Tuple/04_tuple_tie.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | tuple t1(16, "Test", true); 10 | 11 | { 12 | int i = 0; 13 | string str; 14 | bool b = false; 15 | cout << "Before: i = " << i << ", str = \"" << str << "\", b = " << b << endl; 16 | tie(i, str, b) = t1; 17 | cout << "After: i = " << i << ", str = \"" << str << "\", b = " << b << endl; 18 | } 19 | 20 | { 21 | int i = 0; 22 | bool b = false; 23 | cout << "Before: i = " << i << ", b = " << b << endl; 24 | tie(i, std::ignore, b) = t1; 25 | cout << "After: i = " << i << ", b = " << b << endl; 26 | } 27 | return 0; 28 | } -------------------------------------------------------------------------------- /c20_code/07_Tuple/05_tuple_cat.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | tuple t1(16, "Test", true); 10 | tuple t2(3.14, "string 2"); 11 | auto t3 = tuple_cat(t1, t2); 12 | 13 | cout << get<0>(t3) << endl; 14 | cout << get<1>(t3) << endl; 15 | cout << get<2>(t3) << endl; 16 | cout << get<3>(t3) << endl; 17 | cout << get<4>(t3) << endl; 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c20_code/07_Tuple/06_tuple_comparison.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | tuple t1(123, "def"); 10 | tuple t2(123, "abc"); 11 | 12 | if (t1 < t2) { 13 | cout << "t1 < t2" << endl; 14 | } else { 15 | cout << "t1 >= t2" << endl; 16 | } 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c20_code/07_Tuple/07_operator_less_than.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | struct Foo 8 | { 9 | int mInt; 10 | string mStr; 11 | bool mBool; 12 | }; 13 | 14 | bool operator<(const Foo& f1, const Foo& f2) 15 | { 16 | return tie(f1.mInt, f1.mStr, f1.mBool) < 17 | tie(f2.mInt, f2.mStr, f2.mBool); 18 | } 19 | 20 | int main() 21 | { 22 | Foo f1{ 42, "Hello", 0 }; 23 | Foo f2{ 32, "World", 0 }; 24 | cout << (f1 < f2) << endl; 25 | cout << (f2 < f1) << endl; 26 | 27 | return 0; 28 | } 29 | -------------------------------------------------------------------------------- /c20_code/07_Tuple/08_make_from_tuple.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | class Foo 7 | { 8 | public: 9 | Foo(string str, int i) : mStr(str), mInt(i) {} 10 | 11 | private: 12 | string mStr; 13 | int mInt; 14 | }; 15 | 16 | int main() 17 | { 18 | auto myTuple = make_tuple("Hello world.", 42); 19 | auto foo = make_from_tuple(myTuple); 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c20_code/07_Tuple/09_apply.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int add(int a, int b) 7 | { 8 | return a + b; 9 | } 10 | 11 | int main() 12 | { 13 | cout << apply(add, std::make_tuple(39, 3)) << endl; 14 | 15 | return 0; 16 | } -------------------------------------------------------------------------------- /c20_code/07_Tuple/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. -------------------------------------------------------------------------------- /c20_code/08_Filesystem/01_paths.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | using namespace std::filesystem; 6 | 7 | int main() 8 | { 9 | path p1(LR"(D:\Foo\Bar)"); 10 | path p2(L"D:/Foo/Bar"); 11 | cout << p1 << endl; 12 | cout << p2 << endl; 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c20_code/08_Filesystem/02_path_append.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | using namespace std::filesystem; 6 | 7 | int main() 8 | { 9 | path p(L"D:\\Foo"); 10 | p.append("Bar"); 11 | p /= "Bar"; 12 | cout << p << endl; 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c20_code/08_Filesystem/03_path_concat.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | using namespace std::filesystem; 6 | 7 | int main() 8 | { 9 | path p(L"D:\\Foo"); 10 | p.concat("Bar"); 11 | p += "Bar"; 12 | cout << p << endl; 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c20_code/08_Filesystem/04_path_component_iterator.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | using namespace std::filesystem; 6 | 7 | int main() 8 | { 9 | path p(LR"(C:\Foo\Bar)"); 10 | for (const auto& component : p) { 11 | cout << component << endl; 12 | } 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c20_code/08_Filesystem/05_directory_entry.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | using namespace std::filesystem; 6 | 7 | int main() 8 | { 9 | path myPath(L"c:/windows/win.ini"); 10 | directory_entry dirEntry(myPath); 11 | if (dirEntry.exists() && dirEntry.is_regular_file()) { 12 | cout << "File size: " << dirEntry.file_size() << endl; 13 | } 14 | 15 | return 0; 16 | } 17 | -------------------------------------------------------------------------------- /c20_code/08_Filesystem/06_space_info.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | using namespace std::filesystem; 6 | 7 | int main() 8 | { 9 | space_info s = space("c:\\"); 10 | cout << "Capacity: " << s.capacity << endl; 11 | cout << "Free: " << s.free << endl; 12 | 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /c20_code/08_Filesystem/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | 3 | Visual C++ 2017 has the filesystem namespace under std::experimental::filesystem. -------------------------------------------------------------------------------- /c21_code/01_StreamIterators/01_OutputStreamIterators.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | 7 | using namespace std; 8 | 9 | int main() 10 | { 11 | vector myVector(10); 12 | iota(begin(myVector), end(myVector), 1); // Fill vector with 1,2,3...10 13 | 14 | // Print the contents of the vector. 15 | copy(cbegin(myVector), cend(myVector), ostream_iterator(cout, " ")); 16 | cout << endl; 17 | 18 | return 0; 19 | } 20 | -------------------------------------------------------------------------------- /c21_code/01_StreamIterators/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the files in this directory separately. 2 | -------------------------------------------------------------------------------- /c21_code/02_IteratorAdaptors/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the files in this directory separately. 2 | -------------------------------------------------------------------------------- /c21_code/03_WritingAlgorithms/02_IteratorTraitsTest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using std::vector; 6 | using std::cout; 7 | using std::endl; 8 | 9 | template 10 | void iteratorTraitsTest(IteratorType it) 11 | { 12 | typename std::iterator_traits::value_type temp; 13 | temp = *it; 14 | //auto temp = *it; 15 | cout << temp << endl; 16 | } 17 | 18 | int main() 19 | { 20 | vector v{ 5 }; 21 | iteratorTraitsTest(cbegin(v)); 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c21_code/03_WritingAlgorithms/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the files in this directory separately. 2 | -------------------------------------------------------------------------------- /c22_code/01_GridTemplateContainer/GridTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Grid.h" 2 | #include 3 | #include 4 | #include 5 | #include 6 | 7 | using namespace std; 8 | 9 | int main() 10 | { 11 | Grid>> myIntVectorGrid; 12 | Grid>> myIntDequeGrid; 13 | 14 | myIntVectorGrid.at(3, 4) = 5; 15 | cout << myIntVectorGrid.at(3, 4).value_or(0) << endl; 16 | 17 | myIntDequeGrid.at(1, 2) = 3; 18 | cout << myIntDequeGrid.at(1, 2).value_or(0) << endl; 19 | 20 | Grid>> grid2(myIntVectorGrid); 21 | grid2 = myIntVectorGrid; 22 | 23 | //Grid test; // WILL NOT COMPILE 24 | 25 | return 0; 26 | } 27 | -------------------------------------------------------------------------------- /c22_code/02_GridTemplateContainerDefault/GridDefaultTest.cpp: -------------------------------------------------------------------------------- 1 | #include "GridDefault.h" 2 | #include 3 | #include 4 | #include 5 | #include 6 | 7 | using namespace std; 8 | 9 | int main() 10 | { 11 | Grid>> myDequeGrid; 12 | Grid>> myVectorGrid; 13 | Grid myVectorGrid2(myVectorGrid); 14 | 15 | return 0; 16 | } 17 | -------------------------------------------------------------------------------- /c22_code/03_GridTemplateContainerTemplateTemplate/GridTemplateTemplateTest.cpp: -------------------------------------------------------------------------------- 1 | #include "GridTemplateTemplate.h" 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | Grid myGrid; 10 | myGrid.at(1, 2) = 3; 11 | cout << myGrid.at(1, 2).value_or(0) << endl; 12 | 13 | Grid myGrid2(myGrid); 14 | 15 | return 0; 16 | } 17 | -------------------------------------------------------------------------------- /c22_code/04_GridDefaultElementValue/GridTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Grid.h" 2 | #include "SpreadsheetCell.h" 3 | 4 | int main() 5 | { 6 | Grid myIntGrid; // Initial value is 0 7 | Grid myIntGrid2; // Initial value is 10 8 | 9 | myIntGrid.at(1, 2) = 3; 10 | 11 | SpreadsheetCell defaultCell; 12 | //Grid mySpreadsheet; // WILL NOT COMPILE 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c22_code/05_GridDefaultElementValueRef/GridTestRefNonType.cpp: -------------------------------------------------------------------------------- 1 | #include "GridRefNonType.h" 2 | #include "SpreadsheetCell.h" 3 | #include 4 | 5 | using namespace std; 6 | 7 | namespace { 8 | int defaultInt = 11; 9 | SpreadsheetCell defaultCell(1.2); 10 | } 11 | 12 | int main() 13 | { 14 | Grid myIntGrid; 15 | Grid mySpreadsheet; 16 | 17 | Grid myIntGrid2(myIntGrid); 18 | myIntGrid2.at(1, 2) = 3; 19 | 20 | cout << myIntGrid.at(1, 2).value_or(-1) << endl; 21 | cout << myIntGrid2.at(1, 2).value_or(-1) << endl; 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c22_code/06_GridPartialString/GridTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Grid.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | Grid myGrid; 9 | Grid anotherGrid; 10 | 11 | myGrid.at(2, 3) = 45; 12 | anotherGrid = myGrid; 13 | 14 | cout << anotherGrid.at(2, 3).value_or(0) << endl; 15 | 16 | return 0; 17 | } 18 | -------------------------------------------------------------------------------- /c22_code/06_GridPartialString/GridTestString.cpp: -------------------------------------------------------------------------------- 1 | #include "GridString.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | Grid myIntGrid; // Uses the original Grid 9 | Grid myStringGrid; // Uses the partial specialization 10 | // Grid<2, 3> test; // DOES NOT COMPILE! No type specified. 11 | 12 | myStringGrid.at(1, 1) = "Hello"; 13 | Grid myStringGridCopy(myStringGrid); 14 | myStringGridCopy.at(1, 1) = "World."; 15 | 16 | cout << myStringGrid.at(1, 1).value_or("") << endl; 17 | cout << myStringGridCopy.at(1, 1).value_or("") << endl; 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c22_code/06_GridPartialString/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of GridTest.cpp and GridTestString.cpp separately. -------------------------------------------------------------------------------- /c22_code/09_OneDGrid/OneDGridTest.cpp: -------------------------------------------------------------------------------- 1 | #include "OneDGrid.h" 2 | 3 | int main() 4 | { 5 | OneDGrid singleDGrid; 6 | OneDGrid> twoDGrid; 7 | OneDGrid>> threeDGrid; 8 | 9 | singleDGrid[3] = 5; 10 | twoDGrid[3][3] = 5; 11 | threeDGrid[3][3][3] = 5; 12 | 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /c22_code/10_NDGrid/NDGridTest.cpp: -------------------------------------------------------------------------------- 1 | #include "NDGrid.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | NDGrid my3DGrid; 9 | my3DGrid[2][1][2] = 5; 10 | my3DGrid[1][1][1] = 5; 11 | 12 | cout << my3DGrid[2][1][2] << endl; 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c22_code/13_Folding/01_processValues.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | void handleValue(int value) { cout << "Integer: " << value << endl; } 8 | void handleValue(double value) { cout << "Double: " << value << endl; } 9 | void handleValue(string_view value) { cout << "String: " << value << endl; } 10 | 11 | template 12 | void processValues(const Tn&... args) 13 | { 14 | (handleValue(args), ...); 15 | } 16 | 17 | int main() 18 | { 19 | processValues(1, 2, 3.56, "test", 1.1f); 20 | 21 | return 0; 22 | } -------------------------------------------------------------------------------- /c22_code/13_Folding/02_printValues.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | template 6 | void printValues(const Values&... values) 7 | { 8 | ((cout << values << endl), ...); 9 | } 10 | 11 | int main() 12 | { 13 | printValues(1, "test", 2.34); 14 | return 0; 15 | } -------------------------------------------------------------------------------- /c22_code/13_Folding/03_sumValues.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | template 6 | double sumValues(const T& init, const Values&... values) 7 | { 8 | return (init + ... + values); 9 | } 10 | 11 | int main() 12 | { 13 | cout << sumValues(1, 2, 3.3) << endl; 14 | cout << sumValues(1) << endl; 15 | 16 | return 0; 17 | } 18 | -------------------------------------------------------------------------------- /c22_code/13_Folding/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files separately. -------------------------------------------------------------------------------- /c22_code/14_Factorial/01_Factorial.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | template 6 | class Factorial 7 | { 8 | public: 9 | static const unsigned long long val = (f * Factorial::val); 10 | }; 11 | 12 | template<> 13 | class Factorial<0> 14 | { 15 | public: 16 | static const unsigned long long val = 1; 17 | }; 18 | 19 | int main() 20 | { 21 | cout << Factorial<6>::val << endl; 22 | return 0; 23 | } 24 | -------------------------------------------------------------------------------- /c22_code/14_Factorial/02_constexpr.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | constexpr unsigned long long factorial(unsigned char f) 6 | { 7 | if (f == 0) { 8 | return 1; 9 | } else { 10 | return f * factorial(f - 1); 11 | } 12 | } 13 | 14 | int main() 15 | { 16 | constexpr auto f1 = factorial(6); 17 | cout << f1 << endl; 18 | 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c22_code/14_Factorial/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files separately. -------------------------------------------------------------------------------- /c22_code/16_PrintTuple/01_PrintTuple.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | template 8 | class tuple_print 9 | { 10 | public: 11 | tuple_print(const TupleType& t) { 12 | tuple_print tp(t); 13 | cout << get(t) << endl; 14 | } 15 | }; 16 | 17 | template 18 | class tuple_print 19 | { 20 | public: 21 | tuple_print(const TupleType&) { } 22 | }; 23 | 24 | int main() 25 | { 26 | using MyTuple = tuple; 27 | MyTuple t1(16, "Test", true); 28 | tuple_print::value> tp(t1); 29 | 30 | return 0; 31 | } 32 | -------------------------------------------------------------------------------- /c22_code/16_PrintTuple/03_constexpr_if.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | template 8 | class tuple_print_helper 9 | { 10 | public: 11 | tuple_print_helper(const TupleType& t) { 12 | if constexpr(n > 1) { 13 | tuple_print_helper tp(t); 14 | } 15 | cout << get(t) << endl; 16 | } 17 | }; 18 | 19 | template 20 | void tuple_print(const T& t) 21 | { 22 | tuple_print_helper::value> tph(t); 23 | } 24 | 25 | int main() 26 | { 27 | auto t1 = make_tuple(167, "Testing", false, 2.3); 28 | tuple_print(t1); 29 | } 30 | -------------------------------------------------------------------------------- /c22_code/16_PrintTuple/04_constexpr_if_function.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | template 8 | void tuple_print_helper(const TupleType& t) { 9 | if constexpr(n > 1) { 10 | tuple_print_helper(t); 11 | } 12 | cout << get(t) << endl; 13 | } 14 | 15 | template 16 | void tuple_print(const T& t) 17 | { 18 | tuple_print_helper::value>(t); 19 | } 20 | 21 | int main() 22 | { 23 | auto t1 = make_tuple(167, "Testing", false, 2.3); 24 | tuple_print(t1); 25 | } 26 | -------------------------------------------------------------------------------- /c22_code/16_PrintTuple/05_constexpr_if_simplified.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | template::value> 8 | void tuple_print(const TupleType& t) { 9 | if constexpr(n > 1) { 10 | tuple_print(t); 11 | } 12 | cout << get(t) << endl; 13 | } 14 | 15 | int main() 16 | { 17 | auto t1 = make_tuple(167, "Testing", false, 2.3); 18 | tuple_print(t1); 19 | } 20 | -------------------------------------------------------------------------------- /c22_code/16_PrintTuple/06_index_sequence.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | using namespace std; 7 | 8 | template 9 | void tuple_print_helper(const Tuple& t, index_sequence) 10 | { 11 | ((cout << get(t) << endl), ...); 12 | } 13 | 14 | template 15 | void tuple_print(const tuple& t) 16 | { 17 | tuple_print_helper(t, index_sequence_for()); 18 | } 19 | 20 | int main() 21 | { 22 | auto t1 = make_tuple(167, "Testing", false, 2.3); 23 | tuple_print(t1); 24 | } -------------------------------------------------------------------------------- /c22_code/16_PrintTuple/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. -------------------------------------------------------------------------------- /c22_code/17_TypeTraits/02_is_integral.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | template 8 | void process_helper(const T& t, true_type) 9 | { 10 | cout << t << " is an integral type." << endl; 11 | } 12 | 13 | template 14 | void process_helper(const T& t, false_type) 15 | { 16 | cout << t << " is a non-integral type." << endl; 17 | } 18 | 19 | template 20 | void process(const T& t) 21 | { 22 | process_helper(t, typename is_integral::type()); 23 | } 24 | 25 | int main() 26 | { 27 | process(123); 28 | process(2.2); 29 | process("Test"s); 30 | 31 | return 0; 32 | } 33 | -------------------------------------------------------------------------------- /c22_code/17_TypeTraits/03_is_integral_constexpr_if.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | template 8 | void process(const T& t) 9 | { 10 | if constexpr (is_integral_v) { 11 | cout << t << " is an integral type." << endl; 12 | } else { 13 | cout << t << " is a non-integral type." << endl; 14 | } 15 | } 16 | 17 | int main() 18 | { 19 | process(123); 20 | process(2.2); 21 | process("Test"s); 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c22_code/17_TypeTraits/04_is_same.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | template 8 | void same(const T1& t1, const T2& t2) 9 | { 10 | bool areTypesTheSame = is_same_v; 11 | // Pre-C++17: 12 | //bool areTypesTheSame = is_same::value; 13 | cout << "'" << t1 << "' and '" << t2 << "' are "; 14 | cout << (areTypesTheSame ? "the same types." : "different types.") << endl; 15 | } 16 | 17 | int main() 18 | { 19 | same(1, 32); 20 | same(1, 3.01); 21 | same(3.01, "Test"s); 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c22_code/17_TypeTraits/06_doit_enable_if.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | class IsDoable 7 | { 8 | public: 9 | void doit() const { cout << "IsDoable::doit()" << endl; } 10 | }; 11 | 12 | class Derived : public IsDoable 13 | { 14 | }; 15 | 16 | template 17 | enable_if_t, void> 18 | call_doit(const T& t) 19 | { 20 | t.doit(); 21 | } 22 | 23 | template 24 | enable_if_t, void> 25 | call_doit(const T&) 26 | { 27 | cout << "Cannot call doit()!" << endl; 28 | } 29 | 30 | int main() 31 | { 32 | Derived d; 33 | call_doit(d); 34 | call_doit(123); 35 | 36 | return 0; 37 | } 38 | -------------------------------------------------------------------------------- /c22_code/17_TypeTraits/07_doit_constexpr_if.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | class IsDoable 7 | { 8 | public: 9 | void doit() const { cout << "IsDoable::doit()" << endl; } 10 | }; 11 | 12 | class Derived : public IsDoable 13 | { 14 | }; 15 | 16 | template 17 | void call_doit(const T& [[maybe_unused]] t) 18 | { 19 | if constexpr(is_base_of_v) { 20 | t.doit(); 21 | } else { 22 | cout << "Cannot call doit()!" << endl; 23 | } 24 | } 25 | 26 | int main() 27 | { 28 | Derived d; 29 | call_doit(d); 30 | call_doit(123); 31 | 32 | return 0; 33 | } 34 | -------------------------------------------------------------------------------- /c22_code/17_TypeTraits/08_doit_constexpr_if_is_invocable.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | class IsDoable 7 | { 8 | public: 9 | void doit() const { cout << "IsDoable::doit()" << endl; } 10 | }; 11 | 12 | class Derived : public IsDoable 13 | { 14 | }; 15 | 16 | template 17 | void call_doit(const T& [[maybe_unused]] t) 18 | { 19 | if constexpr(is_invocable_v) { 20 | t.doit(); 21 | } else { 22 | cout << "Cannot call doit()!" << endl; 23 | } 24 | } 25 | 26 | int main() 27 | { 28 | Derived d; 29 | call_doit(d); 30 | call_doit(123); 31 | 32 | return 0; 33 | } 34 | -------------------------------------------------------------------------------- /c22_code/17_TypeTraits/09_logical_operator_traits.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | cout << conjunction_v, is_integral> << " "; 9 | cout << conjunction_v, is_integral> << " "; 10 | 11 | cout << disjunction_v, is_integral, is_integral> << " "; 12 | 13 | cout << negation_v> << " "; 14 | 15 | return 0; 16 | } 17 | -------------------------------------------------------------------------------- /c22_code/17_TypeTraits/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | 3 | -------------------------------------------------------------------------------- /c23_code/01_thread/01_ThreadFunction.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | void counter(int id, int numIterations) 7 | { 8 | for (int i = 0; i < numIterations; ++i) { 9 | cout << "Counter " << id << " has value " << i << endl; 10 | } 11 | } 12 | 13 | int main() 14 | { 15 | thread t1(counter, 1, 6); 16 | thread t2(counter, 2, 4); 17 | t1.join(); 18 | t2.join(); 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c23_code/01_thread/03_ThreadLambda.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | int id = 1; 9 | int numIterations = 5; 10 | thread t1([id, numIterations] { 11 | for (int i = 0; i < numIterations; ++i) { 12 | cout << "Counter " << id << " has value " << i << endl; 13 | } 14 | }); 15 | t1.join(); 16 | 17 | return 0; 18 | } 19 | -------------------------------------------------------------------------------- /c23_code/01_thread/04_ThreadMemFunc.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | class Request 7 | { 8 | public: 9 | Request(int id) : mId(id) { } 10 | 11 | void process() 12 | { 13 | cout << "Processing request " << mId << endl; 14 | } 15 | 16 | private: 17 | int mId; 18 | }; 19 | 20 | int main() 21 | { 22 | Request req(100); 23 | thread t{ &Request::process, &req }; 24 | 25 | t.join(); 26 | 27 | return 0; 28 | } 29 | -------------------------------------------------------------------------------- /c23_code/01_thread/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c23_code/03_atomic/01_is_lock_free.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | class Foo { private: int mArray[123]; }; 8 | class Bar { private: int mInt; }; 9 | 10 | int main() 11 | { 12 | atomic f; 13 | cout << is_trivially_copyable_v << " " << f.is_lock_free() << endl; 14 | 15 | atomic b; 16 | cout << is_trivially_copyable_v << " " << b.is_lock_free() << endl; 17 | } 18 | -------------------------------------------------------------------------------- /c23_code/03_atomic/02_inc_func_non_atomic.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | 7 | using namespace std; 8 | 9 | void increment(int& counter) 10 | { 11 | for (int i = 0; i < 100; ++i) { 12 | ++counter; 13 | this_thread::sleep_for(1ms); 14 | } 15 | } 16 | 17 | int main() 18 | { 19 | int counter = 0; 20 | vector threads; 21 | 22 | for (int i = 0; i < 10; ++i) { 23 | threads.push_back(thread{ increment, ref(counter) }); 24 | } 25 | 26 | for (auto& t : threads) { 27 | t.join(); 28 | } 29 | 30 | cout << "Result = " << counter << endl; 31 | 32 | return 0; 33 | } 34 | -------------------------------------------------------------------------------- /c23_code/03_atomic/03_inc_func_atomic.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | using namespace std; 9 | 10 | void increment(atomic& counter) 11 | { 12 | for (int i = 0; i < 100; ++i) { 13 | ++counter; 14 | this_thread::sleep_for(1ms); 15 | } 16 | } 17 | 18 | int main() 19 | { 20 | atomic counter(0); 21 | vector threads; 22 | 23 | for (int i = 0; i < 10; ++i) { 24 | threads.push_back(thread{ increment, ref(counter) }); 25 | } 26 | 27 | for (auto& t : threads) { 28 | t.join(); 29 | } 30 | 31 | cout << "Result = " << counter << endl; 32 | 33 | return 0; 34 | } 35 | -------------------------------------------------------------------------------- /c23_code/03_atomic/05_fetch_add.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | atomic value(10); 9 | cout << "Value = " << value << endl; 10 | int fetched = value.fetch_add(4); 11 | cout << "Fetched = " << fetched << endl; 12 | cout << "Value = " << value << endl; 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c23_code/03_atomic/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c23_code/04_mutex/01_multiple_locks.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | mutex mut1; 6 | mutex mut2; 7 | 8 | void process() 9 | { 10 | //unique_lock lock1(mut1, defer_lock); // C++17 11 | //unique_lock lock2(mut2, defer_lock); // C++17 12 | unique_lock lock1(mut1, defer_lock); 13 | unique_lock lock2(mut2, defer_lock); 14 | lock(lock1, lock2); 15 | // Locks acquired 16 | } // Locks automatically released 17 | 18 | int main() 19 | { 20 | process(); 21 | 22 | return 0; 23 | } 24 | -------------------------------------------------------------------------------- /c23_code/04_mutex/02_scoped_lock.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | mutex mut1; 6 | mutex mut2; 7 | 8 | void process() 9 | { 10 | //scoped_lock locks(mut1, mut2); 11 | scoped_lock locks(mut1, mut2); 12 | 13 | // Locks acquired 14 | } // Locks automatically released 15 | 16 | int main() 17 | { 18 | process(); 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c23_code/04_mutex/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. -------------------------------------------------------------------------------- /c23_code/05_future/03_async.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int calculate() 7 | { 8 | return 123; 9 | } 10 | 11 | int main() 12 | { 13 | auto myFuture = async(calculate); 14 | //auto myFuture = async(launch::async, calculate); 15 | //auto myFuture = async(launch::deferred, calculate); 16 | 17 | // Do some more work... 18 | 19 | // Get the result. 20 | int result = myFuture.get(); 21 | cout << result << endl; 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c23_code/05_future/04_async_error_handling.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | using namespace std; 7 | 8 | int calculate() 9 | { 10 | throw runtime_error("Exception thrown from calculate()."); 11 | } 12 | 13 | int main() 14 | { 15 | // Use the launch::async policy to force asynchronous execution. 16 | auto myFuture = async(launch::async, calculate); 17 | 18 | // Do some more work... 19 | 20 | // Get the result. 21 | try { 22 | int result = myFuture.get(); 23 | cout << result << endl; 24 | } catch (const exception& ex) { 25 | cout << "Caught exception: " << ex.what() << endl; 26 | } 27 | 28 | return 0; 29 | } 30 | -------------------------------------------------------------------------------- /c23_code/05_future/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c25_code/03_NameDB/FirstAttempt/NameDBTest.cpp: -------------------------------------------------------------------------------- 1 | #include "NameDB.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | NameDB boys("boys_long.txt"); 9 | 10 | cout << boys.getNameRank("Daniel") << endl; 11 | cout << boys.getNameRank("Jacob") << endl; 12 | cout << boys.getNameRank("William") << endl; 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c25_code/03_NameDB/SecondAttempt/NameDBTest.cpp: -------------------------------------------------------------------------------- 1 | #include "NameDB.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | NameDB boys("boys_long.txt"); 9 | 10 | cout << boys.getNameRank("Daniel") << endl; 11 | cout << boys.getNameRank("Jacob") << endl; 12 | cout << boys.getNameRank("William") << endl; 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c25_code/03_NameDB/ThirdAttempt/NameDBTest.cpp: -------------------------------------------------------------------------------- 1 | #include "NameDB.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | NameDB boys("boys_long.txt"); 9 | 10 | cout << boys.getNameRank("Daniel") << endl; 11 | cout << boys.getNameRank("Jacob") << endl; 12 | cout << boys.getNameRank("William") << endl; 13 | 14 | return 0; 15 | } 16 | -------------------------------------------------------------------------------- /c26_code/ObjectPoolTest/ObjectPoolTest.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | 5 | TEST_CLASS(ObjectPoolTest) 6 | { 7 | public: 8 | TEST_CLASS_INITIALIZE(setUp); 9 | TEST_CLASS_CLEANUP(tearDown); 10 | 11 | TEST_METHOD(testSimple); // Your first test! 12 | TEST_METHOD(testException); 13 | 14 | TEST_METHOD(testCreation); 15 | TEST_METHOD(testAcquire); 16 | TEST_METHOD(testExclusivity); 17 | TEST_METHOD(testRelease); 18 | }; 19 | -------------------------------------------------------------------------------- /c26_code/ObjectPoolTest/README.txt: -------------------------------------------------------------------------------- 1 | This code is meant to be compiled and executed by the Microsoft 2 | Visual C++ Testing Framework. 3 | 4 | See the detailed discussion in the chapter's text. 5 | 6 | It has been tested with VC++ 2017. -------------------------------------------------------------------------------- /c26_code/ObjectPoolTest/Serial.cpp: -------------------------------------------------------------------------------- 1 | #include "stdafx.h" 2 | #include "Serial.h" 3 | 4 | size_t Serial::sNextSerial = 0; // The first serial number is 0. 5 | 6 | Serial::Serial() 7 | : mSerialNumber(sNextSerial++) // A new object gets the next serial number. 8 | { 9 | } 10 | 11 | size_t Serial::getSerialNumber() const 12 | { 13 | return mSerialNumber; 14 | } 15 | -------------------------------------------------------------------------------- /c26_code/ObjectPoolTest/Serial.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | 5 | class Serial 6 | { 7 | public: 8 | Serial(); 9 | size_t getSerialNumber() const; 10 | 11 | private: 12 | static size_t sNextSerial; 13 | size_t mSerialNumber; 14 | }; 15 | 16 | -------------------------------------------------------------------------------- /c27_code/04_StaticAssert/StaticAssert.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | class Base1 {}; 6 | class Base1Child : public Base1 {}; 7 | 8 | class Base2 {}; 9 | class Base2Child : public Base2 {}; 10 | 11 | template 12 | void process(const T& /*t*/) 13 | { 14 | static_assert(is_base_of_v, "Base1 should be a base for T."); 15 | } 16 | 17 | int main() 18 | { 19 | process(Base1()); 20 | process(Base1Child()); 21 | //process(Base2()); // Error 22 | //process(Base2Child()); // Error 23 | 24 | return 0; 25 | } 26 | -------------------------------------------------------------------------------- /c27_code/05_MemoryErrors/README.txt: -------------------------------------------------------------------------------- 1 | Some compilers might give you warnings or errors when compiling MemoryErrors.cpp. 2 | If your compiler does compile the code, it will most likely crash before 3 | execution can finish. -------------------------------------------------------------------------------- /c27_code/06_ArticleCitations/06_VisualStudio/ArticleCitationsTest.cpp: -------------------------------------------------------------------------------- 1 | #include "ArticleCitations.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | void processCitations(ArticleCitations cit) 7 | { 8 | cout << cit.getArticle() << endl; 9 | int num = cit.getNumCitations(); 10 | for (int i = 0; i < num; i++) { 11 | cout << cit.getCitation(i) << endl; 12 | } 13 | } 14 | 15 | int main() 16 | { 17 | while (true) { 18 | cout << "Enter a file name (\"STOP\" to stop): "; 19 | string fileName; 20 | cin >> fileName; 21 | if (fileName == "STOP") { 22 | break; 23 | } 24 | 25 | ArticleCitations cit(fileName); 26 | processCitations(cit); 27 | } 28 | 29 | return 0; 30 | } 31 | -------------------------------------------------------------------------------- /c27_code/06_ArticleCitations/ArticleCitationsTest.cpp: -------------------------------------------------------------------------------- 1 | #include "01_FirstAttempt/ArticleCitations.h" 2 | #include 3 | 4 | using namespace std; 5 | 6 | void processCitations(ArticleCitations cit) 7 | { 8 | cout << cit.getArticle() << endl; 9 | int num = cit.getNumCitations(); 10 | for (int i = 0; i < num; i++) { 11 | cout << cit.getCitation(i) << endl; 12 | } 13 | } 14 | 15 | int main() 16 | { 17 | while (true) { 18 | cout << "Enter a file name (\"STOP\" to stop): "; 19 | string fileName; 20 | cin >> fileName; 21 | if (fileName == "STOP") { 22 | break; 23 | } 24 | 25 | ArticleCitations cit(fileName); 26 | processCitations(cit); 27 | } 28 | 29 | return 0; 30 | } 31 | -------------------------------------------------------------------------------- /c27_code/06_ArticleCitations/README.txt: -------------------------------------------------------------------------------- 1 | Compile ArticleCitationsTest.cpp with the ArticleCitations.cpp from any 2 | of the subdirectories. You don't need to change the path of the include 3 | of ArticleCitations.h in ArticleCitationsTest.cpp because it is identical 4 | in all subdirectories. 5 | 6 | Example command-line for Linux: 7 | 8 | >g++ -o Test ArticleCitationsTest.cpp 05_FinalVersion/ArticleCitations.cpp 9 | -------------------------------------------------------------------------------- /c27_code/06_ArticleCitations/paper1.txt: -------------------------------------------------------------------------------- 1 | Alan Turing, "On Computable Numbers, with an Application to the Entscheidungsproblem", Proceedings of the London Mathematical Society, Series 2, Vol.42 (1936-37), 230-265. 2 | 3 | Gödel, "Über formal unentscheidbare Sätze der Principia Mathematica und verwandter Systeme, I", Monatshefte Math. Phys., 38 (1931), 173-198. 4 | Alonzo Church. "An unsolvable problem of elementary number theory", American J. of Math., 58 (1936), 345-363. 5 | Alonzo Church. "A note on the Entscheidungsproblem", J. of Symbolic Logic, 1 (1936), 40-41. 6 | E.W. Hobson, "Theory of functions of a real variable (2nd ed., 1921)", 87-88. 7 | -------------------------------------------------------------------------------- /c27_code/06_ArticleCitations/paper2.txt: -------------------------------------------------------------------------------- 1 | Author with no citations 2 | 3 | -------------------------------------------------------------------------------- /c28_code/01_Simple/DerivedSimple.cpp: -------------------------------------------------------------------------------- 1 | #include "DerivedSimple.h" 2 | 3 | DerivedSimple::DerivedSimple() : Simple() 4 | { 5 | // Implementation of constructor 6 | } 7 | 8 | void DerivedSimple::publicMethod() 9 | { 10 | // Implementation of overridden method 11 | Simple::publicMethod(); // You can access base class implementations. 12 | } 13 | 14 | void DerivedSimple::anotherMethod() 15 | { 16 | // Implementation of added method 17 | } 18 | -------------------------------------------------------------------------------- /c28_code/01_Simple/DerivedSimple.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "Simple.h" 4 | 5 | // A derived class of the Simple class. 6 | class DerivedSimple : public Simple 7 | { 8 | public: 9 | DerivedSimple(); // Constructor 10 | 11 | virtual void publicMethod() override; // Overridden method 12 | virtual void anotherMethod(); // Added method 13 | }; 14 | -------------------------------------------------------------------------------- /c28_code/01_Simple/Simple.cpp: -------------------------------------------------------------------------------- 1 | #include "Simple.h" 2 | 3 | int Simple::sStaticInt = 0; // Initialize static data member 4 | 5 | Simple::Simple() : mPublicInteger(40) 6 | { 7 | // Implementation of constructor 8 | } 9 | 10 | void Simple::publicMethod() { /* Implementation of public method */ } 11 | 12 | void Simple::protectedMethod() { /* Implementation of protected method */ } 13 | 14 | void Simple::privateMethod() { /* Implementation of private method */ } 15 | 16 | int main() 17 | { 18 | Simple mySimple; 19 | return 0; 20 | } 21 | -------------------------------------------------------------------------------- /c28_code/02_CopyAndSwap/CopyAndSwap.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | // A simple class that illustrates the copy-and-swap idiom. 4 | class CopyAndSwap 5 | { 6 | public: 7 | CopyAndSwap() = default; 8 | virtual ~CopyAndSwap(); // Virtual destructor 9 | 10 | CopyAndSwap(const CopyAndSwap& src); // Copy constructor 11 | CopyAndSwap& operator=(const CopyAndSwap& rhs); // Assignment operator 12 | 13 | friend void swap(CopyAndSwap& first, CopyAndSwap& second) noexcept; 14 | 15 | private: 16 | // Private data members... 17 | }; 18 | -------------------------------------------------------------------------------- /c28_code/03_Exceptions/Exceptions.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | void throwIf(bool throwIt) 5 | { 6 | if (throwIt) { 7 | throw std::runtime_error("Here's my exception"); 8 | } 9 | } 10 | 11 | int main() 12 | { 13 | try { 14 | throwIf(false); // doesn't throw 15 | throwIf(true); // throws 16 | } catch (const std::runtime_error& e) { 17 | std::cerr << "Caught exception: " << e.what() << std::endl; 18 | return 1; 19 | } 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c28_code/04_FileRead/FileRead.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | ifstream inputFile("FileRead.cpp"); 10 | if (inputFile.fail()) { 11 | cerr << "Unable to open file for reading." << endl; 12 | return 1; 13 | } 14 | 15 | string nextToken; 16 | while (inputFile >> nextToken) { 17 | cout << "Token: " << nextToken << endl; 18 | } 19 | 20 | return 0; 21 | } 22 | -------------------------------------------------------------------------------- /c28_code/05_FileWrite/FileWrite.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | using namespace std; 5 | 6 | int main() 7 | { 8 | ofstream outputFile("FileWrite.out"); 9 | if (outputFile.fail()) { 10 | cerr << "Unable to open file for writing." << endl; 11 | return 1; 12 | } 13 | outputFile << "Hello!" << endl; 14 | outputFile.close(); 15 | 16 | ofstream appendFile("FileWrite.out", ios_base::app); 17 | if (appendFile.fail()) { 18 | cerr << "Unable to open file for appending." << endl; 19 | return 2; 20 | } 21 | appendFile << "Append!" << endl; 22 | 23 | return 0; 24 | } 25 | -------------------------------------------------------------------------------- /c28_code/06_Template/SimpleTemplate.h: -------------------------------------------------------------------------------- 1 | template 2 | class SimpleTemplate 3 | { 4 | public: 5 | SimpleTemplate(T& object); 6 | 7 | const T& get() const; 8 | void set(const T& object); 9 | 10 | private: 11 | T& mObject; 12 | }; 13 | 14 | template 15 | SimpleTemplate::SimpleTemplate(T& object) : mObject(object) 16 | { 17 | } 18 | 19 | template 20 | const T& SimpleTemplate::get() const 21 | { 22 | return mObject; 23 | } 24 | 25 | template 26 | void SimpleTemplate::set(const T& object) 27 | { 28 | mObject = object; 29 | } 30 | -------------------------------------------------------------------------------- /c28_code/06_Template/TemplateTest.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include "SimpleTemplate.h" 4 | 5 | using namespace std; 6 | 7 | int main() 8 | { 9 | // Try wrapping an integer 10 | int i = 7; 11 | SimpleTemplate intWrapper(i); 12 | i = 2; 13 | cout << "wrapped value is " << intWrapper.get() << endl; 14 | 15 | // Try wrapping a string 16 | string str = "test"; 17 | SimpleTemplate stringWrapper(str); 18 | str += "!"; 19 | cout << "wrapped value is " << stringWrapper.get() << endl; 20 | 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /c28_code/08_DoubleDispatch/README.txt: -------------------------------------------------------------------------------- 1 | Compile each of the source files in this directory separately. 2 | -------------------------------------------------------------------------------- /c29_code/02_CarFactory/Car.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | 5 | class Car 6 | { 7 | public: 8 | virtual ~Car() = default; // Always a virtual destructor! 9 | virtual std::string_view info() const = 0; 10 | }; 11 | 12 | class Ford : public Car 13 | { 14 | public: 15 | virtual std::string_view info() const override { return "Ford"; } 16 | }; 17 | 18 | class Toyota : public Car 19 | { 20 | public: 21 | virtual std::string_view info() const override { return "Toyota"; } 22 | }; 23 | -------------------------------------------------------------------------------- /c29_code/02_CarFactory/CarFactory.cpp: -------------------------------------------------------------------------------- 1 | #include "CarFactory.h" 2 | 3 | // Increment the number of cars produced and return the new car. 4 | std::unique_ptr CarFactory::requestCar() 5 | { 6 | ++mNumberOfCarsProduced; 7 | return createCar(); 8 | } 9 | 10 | size_t CarFactory::getNumberOfCarsProduced() const 11 | { 12 | return mNumberOfCarsProduced; 13 | } 14 | 15 | std::unique_ptr FordFactory::createCar() 16 | { 17 | return std::make_unique(); 18 | } 19 | 20 | std::unique_ptr ToyotaFactory::createCar() 21 | { 22 | return std::make_unique(); 23 | } 24 | -------------------------------------------------------------------------------- /c29_code/03_LoggerAdaptor/TestLoggerAdaptor.cpp: -------------------------------------------------------------------------------- 1 | #include "LoggerAdaptor.h" 2 | 3 | int main() 4 | { 5 | NewLoggerAdaptor logger; 6 | logger.log("Testing the logger."); 7 | 8 | return 0; 9 | } 10 | -------------------------------------------------------------------------------- /c30_code/01_PtrSize/PtrSize.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | int main() 6 | { 7 | int *ptr = nullptr; 8 | cout << "ptr size is " << sizeof(ptr) << " bytes" << endl; 9 | 10 | return 0; 11 | } 12 | -------------------------------------------------------------------------------- /c30_code/02_VariableArray/README.txt: -------------------------------------------------------------------------------- 1 | VariableArray.cpp attempts to create a stack-based array using a variable as the size. 2 | This is not a standard C++ feature, although some compilers may allow it. 3 | -------------------------------------------------------------------------------- /c30_code/02_VariableArray/VariableArray.cpp: -------------------------------------------------------------------------------- 1 | int main() 2 | { 3 | int i = 4; 4 | char myStackArray[i]; // Not a standard language feature! 5 | 6 | return 0; 7 | } 8 | -------------------------------------------------------------------------------- /c30_code/03_MixingC/MixingC.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | int main() 4 | { 5 | int class = 1; // Compiles in C, not C++ 6 | printf("class is %d\n", class); 7 | 8 | return 0; 9 | } 10 | -------------------------------------------------------------------------------- /c30_code/03_MixingC/README.txt: -------------------------------------------------------------------------------- 1 | The program MixingC.cpp will not compile in C++, but will compile in C. 2 | -------------------------------------------------------------------------------- /c30_code/04_CSharp/HelloCSharp.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Runtime.InteropServices; 3 | 4 | namespace HelloCSharp 5 | { 6 | class Program 7 | { 8 | [DllImport("HelloCpp.dll", CharSet = CharSet.Unicode)] 9 | public static extern int FunctionInDLL(String s); 10 | 11 | static void Main(string[] args) 12 | { 13 | Console.WriteLine("Written by C#."); 14 | int result = FunctionInDLL("Some string from C#."); 15 | Console.WriteLine("C++ returned the value " + result); 16 | } 17 | } 18 | } 19 | -------------------------------------------------------------------------------- /c30_code/04_CSharp/HelloCpp.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | using namespace std; 4 | 5 | extern "C" 6 | { 7 | __declspec(dllexport) int FunctionInDLL(const wchar_t* p) 8 | { 9 | wcout << L"The following string was received by C++:\n '"; 10 | wcout << p << L"'" << endl; 11 | return 42; // Return some value... 12 | } 13 | } 14 | -------------------------------------------------------------------------------- /c30_code/05_JNI/HelloCpp.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include "HelloCpp.h" 3 | #include 4 | 5 | JNIEXPORT void JNICALL Java_HelloCpp_callCpp(JNIEnv*, jclass) 6 | { 7 | std::cout << "Hello from C++!" << std::endl; 8 | } 9 | -------------------------------------------------------------------------------- /c30_code/05_JNI/HelloCpp.java: -------------------------------------------------------------------------------- 1 | public class HelloCpp { 2 | 3 | static { 4 | System.loadLibrary("hellocpp"); 5 | } 6 | 7 | // This will be implemented in C++ 8 | public static native void callCpp(); 9 | 10 | public static void main(String[] args) 11 | { 12 | System.out.println("Hello from Java!"); 13 | callCpp(); 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /c30_code/06_Perl/README.txt: -------------------------------------------------------------------------------- 1 | To run this example, compile encryptString.cpp into a program named encryptString and execute the perl script with: 2 | 3 | > perl processLog.pl 4 | 5 | -------------------------------------------------------------------------------- /c30_code/06_Perl/encryptString.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | using namespace std; 6 | 7 | string encrypt(string_view input); 8 | 9 | int main(int argc, char* argv[]) 10 | { 11 | if (argc < 2) { 12 | cerr << "Usage: " << argv[0] << " string-to-be-encrypted" << endl; 13 | return -1; 14 | } 15 | 16 | cout << encrypt(argv[1]); 17 | 18 | return 0; 19 | } 20 | 21 | // Performs a very weak form of "encryption" by 22 | // adding 13 to each character of the string. 23 | string encrypt(string_view input) 24 | { 25 | string encrypted = input.data(); 26 | for (auto& character : encrypted) { 27 | character += 13; 28 | } 29 | return encrypted; 30 | } 31 | -------------------------------------------------------------------------------- /c30_code/06_Perl/processLog.pl: -------------------------------------------------------------------------------- 1 | #! /usr/bin/perl 2 | 3 | open (INPUT, "userlog.txt") or die "Couldn't open input file!"; 4 | open (OUTPUT, ">userlog.out") or die "Couldn't open output file!"; 5 | 6 | while ($line = ) { 7 | if ($line =~ m/^Password: (.*)/) { 8 | $result = `./encryptString $1`; 9 | if ($? != 0) { exit(-1); } 10 | print OUTPUT "Password: $result\n"; 11 | } else { 12 | print OUTPUT "$line"; 13 | } 14 | } 15 | 16 | close (INPUT); 17 | close (OUTPUT); 18 | -------------------------------------------------------------------------------- /c30_code/06_Perl/userlog.txt: -------------------------------------------------------------------------------- 1 | Login: bucky-bo 2 | Password: feldspar 3 | 4 | bucky-bo> mail 5 | bucky-bo has no mail 6 | bucky-bo> exit 7 | --------------------------------------------------------------------------------