VB.NET TRAINING GUIDE ERRATA ============================ 70-305 book ----------- p. 1, paragrah 1: "Developing and Implementing Windows-based Applications With Microsoft Visual Basic .NET and Microsoft Visual Studio .NET exam (70-306)" should, of course, be "Developing and Implementing Web Applications with Visual Basic .NET and Visual Studio .NET exam (70-305)" p. 35, Step By Step 1.1: If you get a script runtime error when trying to browse to the new aspx page (expected ; in line 6 char 11), you probably don't have all the pieces installed correctly. You need to install IIS *BEFORE* you install Visual Studio .NET. If you get this error, you may be able to correct it by uninstalling and then reinstalling the .NET Framework. As an alternative, you may be able to fix this problem by registering the ASP.NET extensions with IIS. The ASP.NET file extensions (.aspx and .asmx) must be registered with Internet Information Services (IIS). (In the case that IIS was installed after the .NET Framework was installed, you must run the following application "C:\WINDOWS\Microsoft.NET\Framework\v1.0.3705\aspnet_regiis.exe –i".) p. 65, first line of code: should be p. 65, 3rd line of code: Inherits="Temperature.TemperatureCB" %> should be Inherits="_305C01.Temperature.TemperatureCB" %> p. 68, Step 1: <% Page Language="vb" Inherits="Temperature.TemperatureCB"%> should be <% Page Language="vb" Inherits="_305C01.Temperature.TemperatureCB"%> p. 103, first paragraph:
should be p. 126, Step 6: For i = 0 to intTimes should be For i = 0 to intTimes-1 p. 163, Step by Step 2.13, Step 5. The code in the book is correct; however, there is an error on the CD. The correct line is For i = strPalindrome.Length To 1 Step -1 The CD has the erroneous line For i = strPalindrome.Length-1 To 0 Step -1 p. 167 Step 7: "StepByStep2-12.aspx" should be "GuidedPracticeExercise2-4.aspx" p. 232, step 7 code. Replace the ddlCulture_SelectedIndexChanged procedure with this code: Private Sub ddlCulture_SelectedIndexChanged(ByVal sender As System.Object, _ ByVal e As System.EventArgs) Handles ddlCulture.SelectedIndexChanged ' Set the current cultures to the selected culture Thread.CurrentThread.CurrentCulture = _ New CultureInfo(ddlCulture.SelectedItem.Text) Thread.CurrentThread.CurrentUICulture = _ New CultureInfo(ddlCulture.SelectedItem.Text) ' Refresh the display DisplayData() End Sub (The code on the CD is correct). p. 233, step 7 code. Replace the DisplayData procedure with this code: Private Sub DisplayData() ' Reformat the date according to the user's choices If rbLongDate.Checked Then txtDate.Text = DateTime.Today.ToLongDateString() Else txtDate.Text = DateTime.Today.ToShortDateString() End If ' Update the user interface text Dim rm As ResourceManager = New ResourceManager("_305Ch09.GPE1", _ GetType(GuidedPracticeExercise9_1).Assembly) rbLongDate.Text = rm.GetString("strLongDate") rbShortDate.Text = rm.GetString("strShortDate") End Sub (The code on the CD is correct) p. 245, last paragraph should read as follows: The default use of the Server.Transfer() method passes the form data and the query string of the original page request to the transferred page. But, you can fine-tune this behavior if you like. There's an optional second argument, preserveForm, of the Server.Transfer() method. This second argument takes a Boolean value that indicates whether to preserve form and query string collections. If you supply this value, it defaults to false, but if you don't supply the argument at all, it defaults to true. p. 248, Step 6: StepByStep3_11a.aspx should be StepByStep3_13a.aspx p. 260, first set of answers: The answers should be numbered A, B, C, D instead of A, B, C, E p. 262, answer 14: The correct answer is D (the explanation is correct as printed). p. 270, next to last paragraph: Replace "You'll get a compiler error if you do not follow this rule" with "You may get unexpected results if you do not follow this rule." p. 282, code: The vbCrLf constant won't put a new line into a string rendered by a browser, of course. Replace the Catch block with this code: Catch dte As MyOwnInvalidDateFormatException Dim msg As String ' If some other exception was also ' attached with this exception If Not dte.InnerException Is Nothing Then msg = String.Format("Message:" & _ "
{0}" & _ "

" & _ "Inner Exception:
{1}", _ dte.Message, dte.InnerException.Message) Else msg = String.Format("Message:" & _ "
{0}" & _ "

Help Link:" & _ "
{1}", _ dte.Message, dte.HelpLink) End If lblResult.Text = dte.GetType().ToString() + "
" + msg End Try p. 283, step 2: Add to the end of this step "Name the Label control to hold the results lblResults." p. 284, step 3: Add this additional code at the end of this step: ' Constructor accepting a single string message Public Sub New(ByVal message As String) MyBase.New(message) End Sub p. 296, step 3: Add a WARNING next to this step: ASP.NET Registry Privileges. By default, ASP.NET does not have the required privileges to create an event log. To make this code work, open the machine.config file on your server and change the userName attribute of the processModel element from "machine" to "SYSTEM." You'll need to stop and restart IIS to enable this change to take effect. You should not make this change on a production server, because it lowers the security of ASP.NET. If your server is running Windows Server 2003, the procedure is somewhat different, because this version of Windows does not use the machine.config file. Instead, follow these steps to loosen IIS 6 security: 1. Start Internet Information Services Manager 2. Expand the nodes for your computer and Application Pools 3. Right-click on the DefaultAppPool node and select Properties 4. Select the Identity tab 5. Change the Application pool identity from "Network Service" to "Local System" Again, please do not make these changes on a production server. p. 302, question 2: Replace the first question text with: You are assisting your colleague in solving a logical problem with his code. Sometimes exceptions in his application are not properly handled. The problematic portion of his code is: p. 302, question 2: Replace the text just before the answers with: To make the code function properly, which of the following ways would you modify the code? p. 306, answer to review question 5: delete the phrase "otherwise a compile time error occurs" from the very end of this answer. p. 339, Step 1: StepByStep5-11.aspx should be StepByStep5-12.aspx. p. 351, last sentence on the page: Remove the extra word "The" in the middle of this sentence. p. 357, Step 6: This step should read "In the Generate Dataset window, choose to create a new dsOrders Dataset. Click OK." p. 357, step 7: "SqlDataAdapter1" should be "SqlDataAdapter2" p. 364, Step 7: "Repeater" should be "DataList" p. 370, first line of code on page: "dataase" should be "database" p. 482, last para: "Remove method" should be "Delete method" p. 484, code: Replace this section of code with the corrected version: ' Set up the DataAdapter and fill the DataSet da.SelectCommand = cmdSelect da.DeleteCommand = cmdDelete da.Fill(ds, "Customers") ' Find the specified row and delete it Dim dr As DataRow Dim i As Integer For i = 0 To ds.Tables("Customers").Rows.Count - 1 dr = ds.Tables("Customers").Rows(i) If dr(0) = strCustomerID Then ds.Tables("Customers").Rows(i).Delete() Exit For End If Next ' Save the changes da.Update(ds, "Customers") lblResults.Text = "Row deleted!" End If End Sub p. 488, code: Replace the Private Sub dgCustomers_DeleteCommand with this code: Private Sub dgCustomers_DeleteCommand( _ ByVal source As Object, _ ByVal e As System.Web.UI.WebControls. _ DataGridCommandEventArgs) _ Handles dgCustomers.DeleteCommand ' Find the specified row and delete it Dim strCustomerID As String = _ dgCustomers.DataKeys(e.Item.ItemIndex) Dim dr As DataRow Dim i As Integer For i = 0 To mds.Tables("Customers").Rows.Count - 1 dr = mds.Tables("Customers").Rows(i) If dr(0) = strCustomerID Then mds.Tables("Customers").Rows(i).Delete() Exit For End If Next ' Update the database mda.Update(mds, "Customers") ' And bind the data to the UI LoadData() End Sub p. 523, answer 6: The correct answer is C, not B (the explanation is correct as it stands). p. 529, Step by Step 7.1, Step 3: "Select Add, Add New Component." should be "Select Add, Add Component." p. 535, Step by Step 7.3, Step 3: Replace the line of code Value = mMinValue with mMinValue = Value p. 549, Step by Step 7.10, Step 2. Replace the first part of the code with this corrected code: Imports System.ComponentModel Imports System.Web.UI " & _ (The change is the addition of quotes to the last two lines above.) p. 553, add a new step 4: Open the CompositeControl.vb class and add an attribute to the class definition to tell it which designer is associated with this class: ")> _ Public Class CompositeControl Renumber the existing steps 4 though 9 to be steps 5 through 10. p. 575, Question 8: "menu.ascx" in the question should be "menu.vb". p. 595, Step 3. "Strings.asmx" should be "Customer.asmx" p. 599, Step 3. "CensusService.wsdl" sould be "AirportWeather.wsdl" p. 647 Question 11: Answer D should read: Retrieve a DateTim object from Thread.CurrentThread.CurrentUICulture, and use its methods to format the dates. p. 711 Question 3, Answer D: Oxygen should be Oxygen p. 738, Step 3. Code should be: Imports System.Diagnostics Imports DiagnosticTrace = System.Diagnostics.Trace p. 747, Step 6: Last sentence should end "...process discussed in step 5." p. 773, Step 6: "DataSet1" should be "DataSet11". p. 777, Question 8, answers A, B, C, and D: the first line of code in each answer should be Dim ts As TraceSwitch = New TraceSwitch( _ p. 777, Question 8, answers B and C: #else should be #Else p. 831, last paragraph: "Assemblyinfo.cs" should be "AssemblyInfo.vb" p. 842, step 4: "EventLogApplication.cs" should be "EventLogApplication.vb" p. 843, step 7: Add "You may have to Refresh to see the new EventLogApplication entry." p. 872, outline: "Working with Performance Monitors" should be "Working with Performance Counters" p. 880, step 5: The first procedure in this step should read as follows: Private Sub PopulateLogNames() ddlEventLogs.Items.Clear() ' Add event logs to the DropDownList Dim el As EventLog For Each el In EventLog.GetEventLogs() ddlEventLogs.Items.Add(el.Log) Next End Sub p. 897, last line on page: "for connecting to Oracle database" should be "for connecting to an Oracle database" p. 935, second code snippet: name="DOMAIN\username" should be userName="DOMAIN\username" p. 947, Step 3: "Switch the form to HTML view in the designer" should be "Double-click the form to open its module." p. 947, Step 7: "Switch the form to HTML view in the designer" should be "Double-click the form to open its module." p. 957, Question 8: name="MAIN\Charles" should be userName="MAIN\Charles" p. 1023, paragraph after the Elective Exams bullet list in column 2, should read: You may also count as elective one of the four core exams 70-305, 70-306, 70-315, and 70-316. The elective exam must be from the opposite technology as the exam that you counted as core. For example, if you take the VB Windows-based Applications exam (70-306) as a core exam, you can take either the VB Web Applications exam (70-305) or the C# Web Applications exam (70-315) as an elective. 70-306 book ----------- p. 2, second bullet point: delete this bullet point. The Training Guide series does not use tear cards. p. 37, paragraph directly above Step By Step: "bin\debug" should be "bin" p. 51, step 3: In the code, EditorBrowsableState.Never should be EditorBrowsableState.Always. Otherwise the new property won't be visible in IntelliSense. p. 53, tip: This tip should read: Read-only and Write-only properties. The Get and Set accessors allow you both read and write access to a property. If you would rather make a property read-only, use the ReadOnly keyword in the property declaration and don't include and Set accessor in the property definition. On the other hand, if you just want a write-only property, use the WriteOnly keyword in the property declaration and don't include a Get accessor in the property definition. p. 60, para 2: "Event handlers will normally have a void return type and will accept two arguments." should be "Event handlers will normally accept two arguments and have no return value." p. 61, last para before heading: Both references to Step By Step 1.11 here should be changed to Step By Step 1.9. p. 64, Step 5: Delete this step entirely. p. 65, Step 6: Renumber to step 5. p. 65, Step 3: Code in this step should read: ' Delegate to handle the MouseDown event Sub StepByStep_1_12_MouseDown2(ByVal sender As Object, ByVal e As MouseEventArgs) Dim frm1_12 As Form = CType(sender, Form) If frm1_12.BackColor.ToArgb = Color.AntiqueWhite.ToArgb Then frm1_12.BackColor = Color.LightCoral Else frm1_12.BackColor = Color.AntiqueWhite End If End Sub Private Sub StepByStep1_12_MouseDown(ByVal sender As Object, _ ByVal e As System.Windows.Forms.MouseEventArgs) Handles MyBase.MouseDown MessageBox.Show(String.Format("X ={0}, Y={1}", e.X, e.Y), _ String.Format("The {0} mouse button hit me at:", e.Button.ToString())) End Sub p. 66. Step 4 on Step By Step 1.12 code should read AddHandler Me.MouseDown, _ AddressOf Me.StepByStep_1_12_MouseDown2 p. 70: Add a NOTE to this page: Form Properties. In Step by Step 1.13, Width, Height, and Font are all properties of the form that contains the code. If you prefer, you can write these as Me.Width, Me.Height, and Me.Font, but the compiler will recognize them either way. p. 74, 2nd code in text (starting with Public Sub Drawstring) - delete the semicolon at the end of this code snippet p. 78, code: Change "penYellow" to "penBlue" (2 places) p. 79 para 1: "if the for the VB .NET" should be "for the VB .NET" p. 85, code: "Fill Rectangle" (8th line) should be "FillRectangle" p. 91 step 6 code: If (sbText.Length > 0) Then sbText.Remove(sbText.Length - 1, 1) End If should be If (sbText.Length > 0) Then sbText.Remove( _ sbText.Length - 1, 1) End If p. 93, code: (1) "Cooridnate" should be "Coordinate" (2) "intYCoord += Font.Height" should be "intYCoord += fnt.Height" p. 96, Question 11. Replace all answers with actual VB.NET code: A. Me.Font.Bold = True B. Me.Font = New Font(Me.Font, FontStyle.Bold) C. Me.Font.FontStyle = FontStyle.Bold D. Me.Font = New Font(Me.Font, Me.Font.Bold) p. 97, Question 14 should read "...through an Import statement at the top of the program." instead of "...through a using directive at the top of the program." p. 99, Answer 9: "Graphics.Hwnd" should be "Graphics.FromHwnd" p. 99, Answer 14: In the first line, "Import" should be "Imports". p. 99, Answer 15: "The namespace must be included with a using directive..." should be "The namespace must be included with an Imports directive..." p. 118, Step 10, code: "Attach a event handler" should be "Attach an event handler" p. 119, Step 11, code: "Remove the most recetly added control" should be "Remove the most recently added control" p. 136, Table 2.3, first line: "AcceptReturn" should be "AcceptsReturn" p. 146. Step 3 on Step By Step 2.10 should read: "Change the ListBox control's Name Property to..." (instead of Text property) p. 151, step 4: "th eComboBox" should be "the ComboBox" p. 164, code, about halfway down: tnNode = New TreeNode should be tnNode = New TreeNode(d) p. 169 - something very strange happened with the box around the "Table 2.23" heading. p. 170, Step 4: Replace the code with the following, which accounts for some minor issues when the scrollbar is moved all the way to one end: Private Sub hscr_Scroll(ByVal sender As System.Object, _ ByVal e As System.Windows.Forms.ScrollEventArgs) Handles hscr.Scroll pbImage.Left = CInt(GetHScrollAdjustment()) End Sub Private Sub vscr_Scroll(ByVal sender As System.Object, _ ByVal e As System.Windows.Forms.ScrollEventArgs) Handles vscr.Scroll pbImage.Top = CInt(GetVSCrollAdjustment()) End Sub Private Function GetHScrollAdjustment() As Double Dim hPos As Double = CDbl(hscr.Value - hscr.Minimum) Dim hDiff As Double = CDbl(hscr.Width - pbImage.Width) 'Adjust ticks for scroll thumb width Dim hTicks As Double = CDbl((hscr.Maximum - hscr.LargeChange + 1) - _ hscr.Minimum) GetHScrollAdjustment = (hDiff / hTicks) * hPos End Function Private Function GetVScrollAdjustment() As Double Dim vPos As Double = CDbl(vscr.Value - vscr.Minimum) Dim vDiff As Double = CDbl(vscr.Height - pbImage.Height) 'Adjust ticks for scroll thumb height Dim vTicks As Double = CDbl(vscr.Maximum - vscr.Minimum) GetVScrollAdjustment = (vDiff / vTicks) * vPos End Function p. 185, insert new step 25 to read as follows: 25. Double-click the form to open its module. Add the following line of code at the top of the module: Imports System.IO Then renumber the existing 25 through 29 to be 26 through 30 p. 188, step 7, code: If text <> " then" Then should be If text <> "" Then p. 194 step 6 code: "appriate" should be "appropriate" p. 200, table 2.33, first row: "ActiveMDiChild" should be "ActiveMdiChild" p. 202, step 5. Add at the end of this step: Add an OpenFileDialog component named dlgOpenFile to this form. p. 208, step 7, code: If pos >= ) Then should be If pos >= 0 Then p. 229 step 2: Add "Set the MultiLine property of txtText to True." p. 232 step 2: "lblResults" should be "lblResult" p. 240 step 4: the line of code Dim unhandledException As Exception = + should be Dim unhandledException As Exception = _ (change plus to underscore) p. 240 step 4: The comment ' If no event source exist, create an event source should be ' If no event source exists, create an event source p. 241 third line of code: "Mileage Efficiency Calculator" should be "Mileage Efficiency Calculator Log" p. 266 Answer 9: "contains" should be "contain" p. 266 answer 13: "loose" should be "lose" p. 295, step 7: sf = g.MeasureString(strTime, Font) should be sf = g.MeasureString(strTime, f) and g.DrawString(strTime, Font, New SolidBrush(ForeColor), pos) should be g.DrawString(strTime, f, New SolidBrush(ForeColor), pos) p. 311, last code on page: change this line: lblAddResult.Text = String.Format( _ "The Result of Addition is: {0}", _ intAddResult) p. 319, middle of page: replace "You could also create a RESX file" with "You could also convert a RESX file" p. 319, Step 1: Replace "State" with "Start" p. 325, step 3: Add one more sentence to this step: "Set the Text property of each of the label controls to 0." (That's the numeral zero, and it needs to be set as a numeral, not spelled out) p. 325 step 9: "Exercuse4-1.dll" should be "Exercise4-1.dll" p. 343, Step by Step 5.4 steps 5 and 6: Step5 - Me.BindingContext(mdtBound).Position -=1 Step6 - Me.BindingContext(mdtBound).Position +=1 Should be: Step5 - Me.BindingContext(madtBound).Position -=1 Step6 - Me.BindingContext(madtBound).Position +=1 p. 429, third code section on page should read: UPDATE Products SET Discontinued = 1 FROM Suppliers INNER JOIN Products ON Suppliers.SupplierID = Products.SupplierID WHERE Suppliers.Country = 'Italy' p. 433, Step 6 code: "procedure" should be "' procedure" p. 447 step 4, revised code: Private Sub btnBrowse_Click(ByVal sender As System.Object, _ ByVal e As System.EventArgs) Handles btnBrowse.Click ' Browse for a file to back up Dim dlgOpen As New OpenFileDialog() dlgOpen.Title = "Select a File to back up" dlgOpen.Filter = "All Files(*.*)|*.*" If dlgOpen.ShowDialog = DialogResult.OK Then ' Display the original and backup file names txtFilename.Text = dlgOpen.FileName txtBackupName.Text = dlgOpen.FileName & ".bak" ' Open the file for reading as a stream Dim fsIn As FileStream = _ File.OpenRead(dlgOpen.FileName) ' Open the file for writing as a stream Dim fsOut As FileStream = _ File.OpenWrite(dlgOpen.FileName & ".bak") ' Copy all data from in to out, byte-by-byte Dim b As Int16 = 0 Do While b > -1 b = fsIn.ReadByte() If b > -1 Then fsOut.WriteByte(CType(b, Byte)) End If Loop ' Clean up fsOut.Flush() fsOut.Close() fsIn.Close() End If End Sub p. 449 step 4, revised code: Private Sub btnBrowse_Click(ByVal sender As System.Object, _ ByVal e As System.EventArgs) Handles btnBrowse.Click ' Browse for a file to back up Dim dlgOpen As New OpenFileDialog() dlgOpen.Title = "Select a File to back up" dlgOpen.Filter = "All Files(*.*)|*.*" If dlgOpen.ShowDialog = DialogResult.OK Then ' Display the original and backup file names txtFilename.Text = dlgOpen.FileName txtBackupName.Text = dlgOpen.FileName & ".bak" ' Open the file for reading as a stream Dim fsIn As FileStream = _ File.OpenRead(dlgOpen.FileName) ' Open the file for writing as a stream Dim fsOut As FileStream = _ File.OpenWrite(dlgOpen.FileName & ".bak") ' Copy all data from in to out, using a 4K buffer Dim buf(4096) As Byte Dim intBytesRead As Integer = -1 Do While intBytesRead > 0 intBytesRead = fsIn.Read(buf, 0, 4096) If intBytesRead > 0 Then fsOut.Write(buf, 0, intBytesRead) End If Loop ' Clean up fsOut.Flush() fsOut.Close() fsIn.Close() End If End Sub Page 494, Step 5, Change the code to be as follows: Private Sub btnDelete_Click(ByVal sender As System.Object, _ ByVal e As System.EventArgs) Handles btnDelete.Click ' Prompt the user for a Customer ID Dim strCustomerID As String = _ InputBox("Enter Customer ID to delete:") Dim dr As DataRow Dim i As Integer For i = 0 To mds.Tables("Customers").Rows.Count - 1 dr = mds.Tables("Customers").Rows(i) If dr(0) = strCustomerID Then mds.Tables("Customers").Rows(i).Delete() Exit For End If Next ' Save the changes mda.Update(mds, "Customers") MessageBox.Show("Row deleted!") End Sub p. 531 Answer 6 - the correct answer is B p. 587 Step 3 - "ComboBox" should be "Button" p. 609 step 4 - "sysinfo.ocbx" (at the end of the code line) should be "sysinfo.ocx" p. 642, Chapter 10: A general note: In February 2003, Microsoft announced that they were discontinuing the HTML Help 2.0 compiler and would no longer be releasing it. p. 647, Step 5: (1) "second from" should be "second form" (2) MaximizeButton and MinimizeButton should be MaximizeBox and MinimizeBox, respectively. p. 670, Exam Tip: MinButton and MaxButton should be MinimizeBox and MaximizeBox, respectively. p. 672, first bullet, last line: "AutoDelay" should be "AutomaticDelay" p. 672, last bullet in Review Break: "unobstrusive" should be "unobtrusive" p. 683, Step 6: Add "Imports System.Runtime.Interops" above this code. --------------------------------------------------------------------- p. 695 and after: General corrections to chapter 11: 1) The custom page settings were getting overwritten instead of reused when you clicked the page setup button a second time. The fix is to declare the page settings at the form level: ' Print settings for this page Dim pgsCustom As PageSettings And then revise the button handler to only initialize the settings once: Private Sub btnPageSetup_Click(ByVal sender As System.Object, _ ByVal e As System.EventArgs) Handles btnPageSetup.Click ' Create a PageSettings object if this is the first time in If pgsCustom Is Nothing Then pgsCustom = New PageSettings() End If ' Attach the PageSettings object to the dialog PageSetupDialog1.PageSettings = pgsCustom ' If user clicks OK, make the settings on the document If PageSetupDialog1.ShowDialog = DialogResult.OK Then PrintDocument1.DefaultPageSettings = pgsCustom End If End Sub 2) The Print button wasn't setting the lines count back to zero when called. As a result, if you print twice in the same run, nothing happens the second time. The fix of course is to reset: ' Reset the line counter mintLines = 0 3) Page margins were being ignored because, well, no matter what you did I told the printing to start at x=0, y=0. That's just stupid. Fortunately there is plenty of info passed in to the PrintPage event to do it right. First, the starting Y value needs to be the top of the printable area: ' Vertical position for the next line of text Dim intCurrentY As Integer = e.MarginBounds.Top second, when checking to see whether there's space left for another line, you have to take the top margin into account: ' Check to see whether there's more space on the page If intCurrentY <= e.MarginBounds.Height + e.MarginBounds.Top Then third, when printing, you need to start at the left margin, not at zero: ' Print the text, using the selected font e.Graphics.DrawString(txtText.Text, mfnt, _ Brushes.Black, e.MarginBounds.Left, intCurrentY) 4) Most embarassing of all, there's an off-by-one error that caused it to print the wrong number of lines. The test should be: If mintLines <= nudCopies.Value Then Well, that's all. Now, having fixed all of that, you'll find that there's still a problem: if you use a long test string, it will write all the way to the right margin of the page, ignoring any right margin setting. To fix this would require retrieving the actual text width and doing some wrapping, which would increase the code complexity considerably. The good news is that the exam doesn't get into that level of complexity at all. In fact, you can pass the printing parts of the exam even based on my original incompatent code. --------------------------------------------------------------------- p. 745, Table 12.4, 2nd column, third entry: "refer Table 12.2" should be "refer to Table 12.3" p. 766, step 4 code: "a event" should be "an event" p. 786 step 7 should read: In the Solution Explorer window, select View All Files from the toolbar. Navigate to the bin folder. Right-click the folder and select Include In Project. Then right-click the folder and select Add, Add New Item. Choose to create an XML file, and name the XML file Exercise12-1.exe.config. p. 786 Exercise 12-2. Add a note just after the Estimated Time: NOTE: Debugging SQL Server stored procedures requires the Enterprise Developer or Enterprise Architect version of Visual Studio .NET. If you are using the Professional version, you won't be able to complete this exercise. p. 833, Step 4: "Embedded Resources" should be "Embedded Resource" p. 849, Step 8: Change the last sentence to Set the Value property to [CommonFilesFolder]RandNumCorp\. CommonFilesFolder should not be italicized. p. 861, Step 2: Add one more sentence at the end of this step: Delete the default Class1.vb file. p. 861, Step 3: Add one more line of code at the end of this step: Imports System.Text p. 862 code, about halfway down. Change: "ngen.exe", "\"" + strArgs + " \ "") to "ngen.exe", """" & strArgs & """") p. 889, Step 3: The Bootstrapper code has moved to http://msdn.microsoft.com/vstudio/downloads/tools/bootstrapper/ . Read the documentation on that page for revised instructions. p. 906, Step 4. Add one more sentence at the end of this step: Set the Text property of lblLiveCalculators to 0. p. 922, Step 4. Delete the first line of code (which reads private void PopulateLogNames) p. 923, Step 6. Delete the first two lines of code: private void btnListen_Click(object sender, _ System.EventArgs e) p. 1031, question 59: All references to MinButton and MaxButton should be changed to MinimizeBox and MaximizeBox, respectively. p. 1039, answer 75: "C" should be "D" (the explanation is correct, but the right answer is D). p. 1055, paragraph after the Elective Exams bullet list in column 2, should read: You may also count as elective one of the four core exams 70-305, 70-306, 70-315, and 70-316. The elective exam must be from the opposite technology as the exam that you counted as core. For example, if you take the VB Windows-based Applications exam (70-306) as a core exam, you can take either the VB Web Applications exam (70-305) or the C# Web Applications exam (70-315) as an elective. 70-310 book ----------- p. 86, answer 10: The correct answer is D, not C. p. 561, Table 8.2, description of SetLastError - By default the value is True.