Newtonsoft.Json.Linq.JArray to string array C# - c#

I have a JSON Array like
model.Users = ["Joe","Barny","Power","Tester"]
the model is dynamic
I want to convert model.Users to string[] Users
string[] Users = model.Users
How can I do that?

If model.Users is of type Newtonsoft.Json.Linq.JArray try to call:
string[] Users = model.Users.ToObject<string[]>()

string[] Users = new string[20];
int i = 0;
foreach ( string item in model.Users )
{
Users[i] = item;
i++;
}

Related

How to get distinct values separately in string array?

i have two string array
string[] oldname = ["arun","jack","tom"];
string[] newname = ["jack","hardy","arun"];
here i want compare these two string arrays to get these distinct values separately like :
oldname = ["tom"];
newname = ["hardy"];
how to achieve these ...
string[] oldNameDistinct = oldname.Where(s => !newname.Contains(s)).ToArray();
string[] newNameDistinct = newname.Where(s => !oldname.Contains(s)).ToArray();
Let the two arrays were defined like the following:
string[] oldname = new[] { "arun", "jack", "tom" };
string[] newname = new string[] { "jack", "hardy", "arun" };
Then you can use the Extension method .Except to achieve the result that you are looking for. Consider the following code and the working example
var distinctInOld = oldname.Except(newname);
var distinctInNew = newname.Except(oldname);
Try this :
string[] oldname = new string[] { "arun", "jack", "tom" };
string[] newname = new string[] { "jack", "hardy", "arun" };
List<string> distinctoldname = new List<string>();
List<string> distinctnewname = new List<string>();
foreach (string txt in oldname)
{
if (Array.IndexOf(newname, txt) == -1)
distinctoldname.Add(txt);
}
foreach (string txt in newname)
{
if (Array.IndexOf(oldname, txt) == -1)
distinctnewname.Add(txt);
}
//here you can get both the arrays separately
Hope this help :)
string[] oldname = new []{"arun","jack","tom"};
string[] newname = new []{"jack","hardy","arun"};
// use linq to loop through through each list and return values not included in the other list.
var distinctOldName = oldname.Where(o => newname.All(n => n != o));
var distinctNewName = newname.Where(n => oldname.All(o => o != n));
distinctOldName.Dump(); // result is tom
distinctNewName.Dump(); // result is hardy

Passing multiple selected value from a Listbox to an Array as parameters in C#

Below is my C# code to populate the multi-selected items from the listbox
List<string> listCountry = new List<string>();
for (int i = 0; i < lstCountry.Items.Count; i++)
{
if (lstCountry.Items[i]Selected)
{
countries = listCountry.Add(lstCountry.Items[i].ToString());
}
}
And I have a line to call the method to run the report with the above parameters:
retVal = CR.GetReport(Company, countries);
My question is : What data type should I define for countries since it keeps giving me error like "can't implicitly convert type 'void' to 'string'" when I define countries as
string countries = null;
What did I do wrong here? Please help, thank you very much
Sorry I didn't make it clear enough, I have another the function GetReport() which is defined as
public CrystalDecisions.CrystalReports.Engine.ReportDocument GetReport( string Company, string countries)
{
CrystalDecisions.CrystalReports.Engine.ReportDocument retVal = new rptReortData();
ReportLogon rptLog = new ReportLogon();
rptLog.logon(retVal, "Report");
retVal.SetParameterValue("P_Country", new string[] { country});
}
How do I get the value from the listbox assign to countries
You didn't provide the name of your function but I guess it's GetReport. It doesn't return any value so you can't assign the retVal. Try the below:
CR.GetReport(Company, countries);
I'm a little puzzled by your question, but I'm guessing that the CR.GetReport function is raising an exception? So your data-type for countries depends on that function.
I might make the following change:
listCountry.Add((lstCountry.Items[i] == null ? string.Empty : lstCountry.Items[i].ToString()));
List<string> listText = new List<string>();
List<string> listValue = new List<string>();
foreach (int index in ListBox1.GetSelectedIndices()) {
listText.Add(ListBox1.Items[index].Text);
listValue.Add(ListBox1.Items[index].Value);
}
You need to return retVal from your function
public CrystalDecisions.CrystalReports.Engine.ReportDocument GetReport( string Company, string countries)
{
CrystalDecisions.CrystalReports.Engine.ReportDocument retVal = new rptResearchDataDownload();
ReportLogon rptLog = new ReportLogon();
rptLog.logon(retVal, "Report");
retVal.SetParameterValue("P_Country", new string[] { country});
// ADD THIS LINE
return retVal;
}
Also you need convert the list to a string. You can do this like this:
countries = listCountry.Aggregate((list, c) => list + c + ",");

C# Creating named object for each object in LDAP DirectorySearch to insert into SQL database

Ive created a Directory Searcher to pull multiple properties from each user.
objSearchADAM = new DirectorySearcher(objADAM);
objSearchADAM.PropertiesToLoad.Add("givenname");
objSearchADAM.PropertiesToLoad.Add("lastlogontimestamp");
ect...
objSearchResults = objSearchADAM.FindAll();
I then enumerate them, and convert the interger8 timestamp to standard date/time, and save to csv file with
List<string> timeProps = new List<string>() { "lastlogontimestamp", "accountexpires", "pwdlastset", "lastlogoff", "lockouttime", "maxstorage", "usnchanged", "usncreated", "usndsalastobjremoved", "usnlastobjrem", "usnsource" };
foreach (SearchResult objResult in objSearchResults)
{
objEntry = objResult.GetDirectoryEntry();
ResultPropertyCollection myResultProp = objResult.Properties;
foreach (string myKey in myResultProp.PropertyNames)
{
foreach (Object myCollection in myResultProp[myKey])
{
Object sample = myCollection;
if (timeProps.Contains(myKey))
{
String times = sample.ToString();
long ft = Int64.Parse(times);
DateTime date;
try
{
date = DateTime.FromFileTime(ft);
}
catch (ArgumentOutOfRangeException ex)
{
date = DateTime.MinValue;
Console.WriteLine("Out of range: " + ft);
Console.WriteLine(ex.ToString());
}
sample = date;
Console.WriteLine("{0}{1}", myKey.PadRight(25), sample);
objWriter.WriteLine("{0}{1}", myKey.PadRight(25), sample);
}
else
{
Console.WriteLine("{0}{1}", myKey.PadRight(25), sample);
objWriter.WriteLine("{0}{1}", myKey.PadRight(25), sample);
}
}
now i need to create an object for each user with the strings from each result that i can put into an SQL command ive built. where the LDAP query to SQL would be givenname = FirstName and lastlogontimestamp = LastLogon and so on.
StringBuilder sb = new StringBuilder();
sb.Append("INSERT INTO activedirectory.dimUserST (FirstName, LastName) VALUES (#FirstName, #LastName)");
loadStagingCommand.Parameters.AddWithValue("#FirstName", FirstName).DbType = DbType.AnsiString;
ect...
loadStagingCommand.CommandText = sb.ToString();
loadStagingCommand.ExecuteNonQuery();
i tried to use IDictionary in my first foreach (similar to code found here http://ideone.com/vChWD ) but couldn't get it to work. I read about IList and reflection, but im not sure how i could incorporate these.
UPDATE
I researched and found ExpandoObjects and attempted to write in code based off of what i saw in here Creating Dynamic Objects
however i run this new code I return "employeenumber System.Collections.Generic.List`1[System.Dynamic.ExpandoObject]"
if(employeeNumber.Contains(myKey))
{
string[] columnNames = { "EmployeeNumber" };
List<string[]> listOfUsers = new List<string[]>();
for (int i = 0; i < 10; i++)
{
listOfUsers.Add(new[] { myKey});
}
var testData = new List<ExpandoObject>();
foreach (string[] columnValue in listOfUsers)
{
dynamic data = new ExpandoObject();
for (int j = 0; j < columnNames.Count(); j++)
{
((IDictionary<String, Object>)data).Add(columnNames[j], listOfUsers[j]);
}
testData.Add(data);
Console.WriteLine("{0}{1}", myKey.PadRight(25), testData);
objWriter.WriteLine("{0}{1}", myKey.PadRight(25), testData);
}
}
I am obviously missing something here and cant seem to wrap my head around what the problem is. I might even be going about this the wrong way. Basically all i need to do is pull users and their properties from Active Directory and put into SQL database tabels. And I've worked out how to do both separately, but I cant figure out how to put it all together.
If the CSV is just being used to cache the results, you could use a Dictionary to store the contents of the search results instead. Separating your code into functions could be helpful:
private static object GetFirstValue(ResultPropertyCollection properties,
string propertyName)
{
var propertyValues = properties[propertyName];
var result = propertyValues.Count == 0 ? null : propertyValues[0];
return result;
}
Then you could either use a dictionary to hold the property values, or you could create a type:
var results = new List<Dictionary<string, object>>();
foreach(SearchResult objResult in objSearchResults)
{
var properties = objResult.Properties;
var propertyDictionary = new Dictionary<string, object> {
{"FirstName", GetFirstValue(properties, "givenname")},
{"LastName", GetFirstValue(properties, "sn")},
{"UserName", GetFirstValue(properties, "samaccountname")},
};
results.Add(propertyDictionary);
}
Now you have a list of property bags.
This could also be a simple LINQ statement:
var results = objSearchResults.OfType<SearchResult>()
.Select(s => s.Properties)
.Select(p => new {
FirstName = (string)GetFirstValue(properties, "givenname"),
LastName = (string)GetFirstValue(properties, "sn"),
UserName = (string)GetValue(properties, "samaccountname"),
AccountExpires = GetDateTimeValue(properties, "accountexpires")
});
Use the dictionaries like this:
foreach(var item in results)
{
var command = new SqlCommand();
...
command.Parameters.AddWithValue("firstName", item["FirstName"]);
...
}

How to convert List to a string and back

I retrieved a list of users from database, something like
List<User> users = <..list of users from db...>
Name, LastName, DateOfBirth //multidimensional array??
Now I want to store this list as a string and I want be able to reuse it i.e.
string strUsers = users.ToArray().ToString();
How to recreate a list of users from strUsers?
Is it possible?
Use the string.Join method, e.g.
var joined = string.Join(",", users.Select(u => u.Name));
This would give you a single string of user's names separated by ','.
Or for multiple columns:
var joined = string.Join(",",
users.Select(u => u.FirstName + " " + u.LastName ));
You can reverse the process using string.Split, e.g.
var split = joined.Split( new [] {','} );
If you have a lot of users and a lot of columns, it would be better to write your own custom converter class.
public static class UsersConverter
{
// Separates user properties.
private const char UserDataSeparator = ',';
// Separates users in the list.
private const char UsersSeparator = ';';
public static string ConvertListToString(IEnumerable<User> usersList)
{
var stringBuilder = new StringBuilder();
// Build the users string.
foreach (User user in usersList)
{
stringBuilder.Append(user.Name);
stringBuilder.Append(UserDataSeparator);
stringBuilder.Append(user.Age);
stringBuilder.Append(UsersSeparator);
}
// Remove trailing separator.
stringBuilder.Remove(stringBuilder.Length - 1, 1);
return stringBuilder.ToString();
}
public static List<User> ParseStringToList(string usersString)
{
// Check that passed argument is not null.
if (usersString == null) throw new ArgumentNullException("usersString");
var result = new List<User>();
string[] userDatas = usersString.Split(UsersSeparator);
foreach (string[] userData in userDatas.Select(x => x.Split(UserDataSeparator)))
{
// Check that user data contains enough arguments.
if (userData.Length < 2) throw new ArgumentException("Users string contains invalid data.");
string name = userData[0];
int age;
// Try parsing age.
if (!int.TryParse(userData[1], out age))
{
throw new ArgumentException("Users string contains invalid data.");
}
// Add to result list.
result.Add(new User { Name = name, Age = age });
}
return result;
}
}
You will win performance wise using the StringBuilder to build up your users string. You could also easily expand the converter to take account different separators/additional logic etc.
If you need a more generic solution (to be able to use for any class), you could create a converter which uses reflection to iterate over all the public fields, get/set properties to see what can be extracted as string and later reverse the process to convert your string back to the list.
I think what you're looking for is something that lets you dump all users to a string and get the users back from the string, correct?
I suggest something like this:
Add a method that returns an XElement to the Users type:
public XElement GetXElement()
{
return new XElement("User", new XElement("Name", this.FirstName)) //and so on...
}
and then one that decodes the string into a user:
static User GetUserFromXElement(string xml)
{
XElement temp = XElement.Parse(xml);
User temp = new User();
foreach (XElement inner in temp.Elements())
{
switch inner.Name
{
case "Name":
temp.Name = inner.Value
break;
//whatever
}
}
}
And then do this:
public string UsersToElements (List<Users> toWrite)
{
Stringbuilder sb = new StringBuilder();
StringWriter sw = new StringWriter(sb);
XElement root = new XElement("root");
XDocument temp = new XDocument(root);
foreach (User user in toWrite)
{
root.Append(user.GetXElement());
}
temp.Save(sw);
return sw.ToString();
}
and this:
public List<Users> ElementsToUsers (string xml)
{
List<Users> usrsList = new List<Users>();
XDocument temp = XDocument.Load(xml);
foreach (XElement e in XDocument.Root.Elements())
{
usrsList.Append(Users.GetUserFromXElement(e));
}
return usrsList;
}
JSON solution (using JSON.NET)
public JObject GetJObject()
{
return new JObject("user", new JProperty("name", this.FirstName)); //so on
}
static User GetUserFromJObject(string json)
{
JObject obj = JObject.Parse(json);
return new User() { FirstName = (string)obj["user"]["name"] }; //so on
}
public string UsersToElements (List<Users> users)
{
JObject root = new JObject(from usr in users select new JAttribute("user", usr.GetJObject());
return root.ToString();
}
public List<users> ElementsToUsers(string json)
{
List<Users> users = new List<Users>();
JObject temp = JObject.Parse(json);
foreach (JObject o in (JEnumerable<JObject>)temp.Children())
{
users.Add(Users.GetUserFromJObject(o.ToString());
}
return users;
}
I have no idea if ths works :/ (well the XML I know it does, not so sure about the JSON)
Use this code
string combindedString = string.Join( ",", myList );
var Array = combindedString.Split( new [] {','} );

Converting the value of a string to a variable of KeyValuePair<TKey,TValue>

I was doing something like this :
foreach( KeyValuePair<int,SOME_CLASS> reader in _readerDict )
{
var selectedReader = reader;
var antenna1 = selectedReader.Value.Antenna1IsEnabled;
var antenna2 = selectedReader.Value.Antenna2IsEnabled;
var antenna3 = selectedReader.Value.Antenna3IsEnabled;
var antenna4 = selectedReader.Value.Antenna4IsEnabled;
}
But then again I want to do something like the following :
foreach( KeyValuePair<int,SOME_CLASS> reader in _readerDict )
{
var selectedReader = reader;
for( var idx = 1; idx <= 4; idx++ )
{
var antennaIsEnabled = string.Format( "selectedReader.Value.Antenna{0}IsEnabled", idx );
// cast the value of antennaIsEnabled as a KeyValuePair<int,SOME_CLASS> variable datatype here
....
}
}
Is there anyway for me to cast the value of antennaIsEnabled as a KeyValuePair variable datatype?
I suppose you want to extract the selectReader as key and AntennaIsEnabled as value
string[] parts = strA.Split('.');
var list = new List<KeyValuePair<string, string>>();
list.Add(new KeyValuePair<string, string>(part[0], part[2]));
Need to add some error checking...
It sounds like you want a result that looks like this:
Dictionary<int, bool> AntennaIsEnabled = new Dictionary<int, bool>();
foreach( KeyValuePair<int,SOME_CLASS> reader in _readerDict )
{
var selectedReader = reader;
//From your example
AntennaIsEnabled.Add(1, selectedReader.Value.Antenna1IsEnabled);
AntennaIsEnabled.Add(2, selectedReader.Value.Antenna2IsEnabled);
AntennaIsEnabled.Add(3, selectedReader.Value.Antenna3IsEnabled);
AntennaIsEnabled.Add(4, selectedReader.Value.Antenna4IsEnabled);
}
Then you can access the state of each antenna by using a syntax like AntennaIsEnabled[2].
Try using FastMember library to access your properties as strings.

Categories