Click here to Skip to main content
15,891,136 members
Please Sign up or sign in to vote.
0.00/5 (No votes)
See more:
This is my first derived class and I'm so confused. I don't understand how these two classes communicate.

I'm expecting to have to initialize the base class and then initialize the derived class, because it looks that way int he example I'm looking at.

I was hoping to create a derived class that inherits some methods and fields from a base class that has already been initialized. I hope I'm being clear, but if not, please excuse my frustration and allow me to elaborate.

My Base Class:

using System;

namespace RickRoll
{
	public class DbDataSource
	{
		public string FilePath { get; }
		public string Server { get; }
		public string DataSource { get; }
		
		public DataFileType FileType { get; }
		public bool DataSourceIsFile { get; }


		/// <summary>
		/// The data source will be set to fhe file path unless server is null
		/// </summary>
		/// <param name="dbfilepath"></param>
		/// <param name="dbserver"></param>
		public DbDataSource(string dbfilepath, string dbserver)
		{
			FilePath = dbfilepath;
			Server = dbserver;
			FileType = GetDbFileType (dbfilepath);
			DataSource = dbserver ?? FilePath;                          // Set DataSource = Server.  If Server is null, set DataSource = file path
			DataSourceIsFile = (DataSource == dbfilepath);			// If DataSource = file path, DataSourceIsFile = true
		}

		/// <summary>
		/// DataFileType by File Extension
		/// </summary>
		/// <param name="path"></param>
		/// <returns></returns>
		private DataFileType GetDbFileType(string path)
		{
			DataFileType ft;
			string ext;
			if (path.Contains ("."))
			{
				string fpath = path.Replace ("|DataDirectory|" , AppDomain.CurrentDomain.BaseDirectory);
				ext = System.IO.Path.GetExtension (fpath).Replace ("." , "").ToUpper ( );
				ft = (DataFileType) Enum.Parse (typeof (DataFileType) , ext);           /// throw exception if extention is not in DataFileType enum or is null
			}
			else
			{
				ft = (DataFileType) Enum.Parse (typeof (DataFileType) , path.ToUpper ( ));           /// throw exception if extention is not in DataFileType enum or is null
			}
			return ft;
		}

		// <summary>
		/// Int enumeration of the supported file types
		/// </summary>
		public enum DataFileType
		{
			None,
			MDB = 1,       // 0 = not a configured data file
			ACCDB,
			MDF,           // Primary Data FIle
			NDF,           // File Group (secondary data files)
			XLS,           // Excel 97-2003 worksheet
			XLSX,          // Excel 2007 workbook
			XLSXM,         // Macro enabled workbook
			XLTM,          // Binary worksheet (BIFF12)
			XLW,           // Excel works space, previously known as workbook
			CSV,           // Comma separated values
			TAB,           // Tab separated values
			TSV,           // Tab separated values
			TXT            // Delimited Text file
		}

	}
}

My Derived class:

using System;

namespace RickRoll
{
	public class DbPRovider : DbDataSource
	{
		public DataProvider Provider { get; set; }

		public DbPRovider()
		{
			Provider = GetDbProvider (DbDataSource.FilePath);
		}

		/// <summary>
		/// Int enumeration of suported data sources
		/// </summary>
		public enum DataProvider
		{
			None,
			Microsoft_ACE_OLEDB_12_0 = 1,          // Microsoft.ACE.OLEDB.12.0 - MS OLEDB DataProvider for MDB or ACCDB or EXCEL
			Microsoft_ACE_OLEDB,               // Microsoft.ACE.OLEDB VersionIndependentProgID
			Microsoft_Jet_OLEDB_4_0,           // MS Access - Does not work with ACCDB or any SQL Server version
			Microsoft_Jet_OLEDB,               // Version Independent ProgID
			SQLNCLI11,                         // SQL Server Native Client for OleDb
			SQLNCLI,                           // Version Independent ProgID
			SQLOLEDB_1,                        // SQL Server OleDb - Does not work with SQL Server Express
			SQLOLEDB,                          // VersionIndependentProgID
			SQL__Server__Native__Client__11_0, // SQL Server Native Client using ODbC
			SQL__Server__Native__Client,       // Version Independent ProgID
			MSDASQL_1,                         // Microsoft OleDb Data Access Components using ODbC
			MSDASQL                            // Version Independent ProgID
		}



		private DataProvider GetDbProvider(DataFileType ft)
		{
			switch (ft)
			{
				case DataFileType.MDB:
				case DataFileType.ACCDB:
					return DataProvider.Microsoft_ACE_OLEDB_12_0;
				case DataFileType.MDF:
					return DataProvider.SQLNCLI11;                 // SQLOLEDB_1 and SQLOLEDB did not work with SQL Server Express
				case DataFileType.NDF:
					return DataProvider.SQLNCLI11;
				case DataFileType.XLS:
				case DataFileType.XLSX:
				case DataFileType.CSV:
				case DataFileType.TAB:
				case DataFileType.TSV:
				case DataFileType.TXT:
					return DataProvider.Microsoft_ACE_OLEDB_12_0;
				default:
					throw new ArgumentException ($"* * * DataFileType is not a supported data file format.  Database DataProvider could not be determined.");
			}
		}


	}
}


What I have tried:

I'm getting errors here:

public DbPRovider()
		{
			Provider = GetDbProvider (DbDataSource.FilePath);
		}


There is no argument given that corresponds to the required formal parameter dbfilepath.

What's the point of deriving from a class, if you have to assign its members? I don't get it.

Very frustrating.
Posted
Updated 17-Feb-18 18:09pm
Comments
johannesnestler 19-Feb-18 9:08am    
so all Solutions good and right - but what you have here is just a missunderstanding in how the constructors are callled. so your baseclass constructor should be called with some Default Parameters by the constructor of the derived class. So your baseclass constructor will run and your fields are initialized - So OOP works as you expected - just read about constructors again on MSDN or your favorite book...

What's the point of deriving from a class, if you have to assign its members?
Inheritance in C# is a compile-time "copying," or transmission, of structure.

It is not a copying of an instance of a Class, and the current values of Fields and/or Properties of the Class instance, to another instance.

If you want Fields and/or Properties to persist their current values in derived Classes: use static declared implementation.

If you want each creation of a new instance of a derived Class to initialize certain values, you can do that in the Class constructor in the base Class. You can define Constants, Fields, etc., and, as long as their values are present at compile time, derived Class instances will share those values.

The "point" of Inheritance is that it is a key component of OOP, and facilitates code re-use, separation of concerns, and the modeling of relationships, hierarchies, etc.

Let me know if this is helpful.
 
Share this answer
 
Comments
[no name] 18-Feb-18 3:23am    
Thanks, Bill! I bit off more than I could chew, trying to tackle Interfaces, Inheritance, Abstract classes all at the same time. I have never coded an Interface or an inherited class and the large number of examples that try to describe this topic using "class A, class B, and class C" leaves my head spinning.

If you want Fields and/or Properties to persist their current values in derived Classes: use static declared implementation.

I used static fields originally, but then I changed it because I read that 1) you should never use static fields because of something to do with multi-threaded environments and 2) a static member takes up one space in memory. That made me think, that changing the static member's value in my class, must also change it's value everywhere the static field is referenced.

What I'm really struggling with is taking something that worked and made sense to me and turning it into something that adheres to OOP principles.

I'm going to have to sit on this overnight and really try to understand everything you've said. I'm probably too frustrated to make that happen this evening though. Thank you so much!
BillWoodruff 18-Feb-18 4:19am    
Hi, Rick, Not to worry, it takes a while to digest OOP in C#.

I find it helps my students to think of 'blueprints" when it comes to inheritance. The blueprint specifies structure.

The Abstract Class can both specify structure and provide implementation. Virtual Ckasses are another story.

I use the analogy of a "Bill of Materials" to describe Interfaces: it is not only a specification of structure, but a contract that tells what a Class that uses it must implement/provide.

A static declared Class, Property, Method, or Field, becomes a one-only implementation that is available to every derived Class instance; yes, there can be (multi) threading issues with static entities, but, they are widely useful.
[no name] 19-Feb-18 0:27am    
This is an exceptional description. I put it on the whiteboard in my bedroom. Yes, I have a whiteboard in my bedroom. Three of them. And a chalkboard. This stuff is hard. LOL
To access members from an inherited class you have to use the 'base' keyword:
C#
Provider = GetDbProvider(base.FilePath);
// or just the member name:
Provider = GetDbProvider(FilePath);

In your code 'DbDataSource' is a (class) type, not an object you can use in the way you try to do.
https://docs.microsoft.com/en-us/dotnet/csharp/programming-guide/classes-and-structs/inheritance[^]
 
Share this answer
 

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



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