char to string error - c#

I'm currently just 2 errors away from a working program. I'll post the line that contains error and the definition of its variable and finally the errors. Please tell me where i got wrong. Thank you.
private Dictionary<string, bool[]> letterData = new Dictionary<string, bool[]>();
public char[] mapNeurons()
{
char[] map = new char[this.letters.Items.Count];
for (int i = 0; i < map.Length; i++)
{
map[i] = '?';
}
for (int i = 0; i < this.letters.Items.Count; i++)
{
double[] input = new double[Form1.DOWNSAMPLE_HEIGHT * Form1.DOWNSAMPLE_WIDTH];
char ch = ((string)(this.letters.Items[i]))[0];
bool[] data = this.letterData[ch]; //line contains errors
for (int j = 0; j < input.Length; j++)
{
input[j] = data[j] ? 0.5 : -0.5;
}
int best = this.network.Winner(input);
map[best] = ch;
}
return map;
}
and here are the error
Error 1 The best overloaded method match for 'System.Collections.Generic.Dictionary.this[string]' has some invalid arguments
Error 2 Argument '1': cannot convert from 'char' to 'string'
I used Char instead of String because if using String it will return the whole line of the string loaded, i just wants to return the first letter of the string
for example: data = A1:000001100000000110000000111000000011100000001
if use string it will return the whole line, i just wants it to return 'A'
NEW IDENTIFIED PROBLEM:
when i enter the data, i put the data into 'A1' key, which explain why im using string, so when it didnt find 'A1' because it is char, it just find 'A' thats why it returned '?', is it possible if i use string n just read the first character which is 'A' in the string line?

First of all, you need to add items to the dictionary with the Add() method.
Secondly, your dictionary's key is a string, so you need to use a string as the index ... you can get the string representation of a char by calling ToString() on the char instance.
char ch = 'x';
private Dictionary<string, bool[]> letterData = new Dictionary<string, bool[]>();
letterData.Add(ch.ToString(), new []{true, false});
bool[] data = this.letterData[ch.ToString()];
Or change the index to char:
char ch = 'x';
private Dictionary<char, bool[]> letterData = new Dictionary<char, bool[]>();
letterData.Add(ch, new []{true, false});
bool[] data = this.letterData[ch];

bool[] data = this.letterData[ch.ToString()];

To convert char to string, ToString() can be called. This is the solution for the question.
But hafizhans, was working on some program, for which he had asked question, where he converted the Dictionary<char, bool[]> to Dictionary<string, bool[]>. Now he was storing the data from dictionary to text file something like this
A1:001110000111100001010100
Now while reading this, he only needed A1 part, so Split function did the trick.

UPDATED
Try this:
if(this.letterData.ContainsKey(ch.ToString()))
bool[] data = this.letterData[ch.ToString()];
or
if(this.letterData.ContainsKey(ch.ToString()))
bool[] data = this.letterData[ch+""];

the variable ch is most likely a char you have to use a string instead

Try the following:
char charString = 'a';
if (letterData.ContainsKey(charString.ToString()))
{
// Found
}

How about changing to:
string sCh = ch.ToString();
bool[] data = null;
if (this.letterDate.ContainsKey(sCh)
{
data = this.letterData[sCh];
}
In addition, you may want consider changing the key on the dictionary to be Char instead.

Related

How do I add integers to char[] array?

So I have to write a code that picks our random numbers from 1 to 100 and add them to a char[] array. But I'm having some difficulty doing so as I can only add the numbers to the array if I convert them to a char using (char) which changes the number. Can someone please help me?
Thanks,
public char[] CreationListe(int nmbrevaleurTirés)
{
char[] l = new char[nmbrevaleurTirés];
for (int i = 0; i < nmbrevaleurTirés; i++)
{
l[i] = (char)(new Random().Next(1, 101));
}
return l;
}
use ToChar() method of Convert class.
Convert.ToChar(new Random().Next(1, 101))
You cannot convert an integer larger then 9 into a char because it's considered as 2 chars, i.e. 10 will be considered as 1 and 0.
so I would recommend adding it to an array of strings
(except if your trying to get a random charcode which I dont think is the case, because why till 100?)
Personally, I'd use an int[] array instead
There shouldn't be any problem in storing ints up to 65535 in a char but you will have to cast it back to an int if you don't want it to be weird:
public static void Main()
{
var x = CreationListe(200);
foreach(var c in x)
Console.WriteLine((int)c); //need to cast to int!
}
public static char[] CreationListe(int nmbrevaleurTirés)
{
char[] l = new char[nmbrevaleurTirés];
for (int i = 0; i < nmbrevaleurTirés; i++)
{
l[i] = (char)(new Random().Next(1, 65536));
}
return l;
}
https://dotnetfiddle.net/z5yoBn
If you don't cast it back to int, then you'll get the char at that character index in the unicode table. If you've put 65 into a char, you'll get A when you print it, for example. This is because A is at position 65 in the table:
(ASCII table image posted for brevity's sake)

Getting error while using split method for reading multiple integers in a single line

I am getting an error while using Split while reading an integer from the user
int[] a = new int[s];
for (i = 0; i < s; i++)
{
a[i] = Int32.Parse(Console.ReadLine().Split(' '));
}
Can you please help me how to use Split.
LINQ can really help you here:
int[] a = Console.ReadLine().Split(' ').Select(int.Parse).ToArray();
Since split returns an array, and each time you need the i'ed one, you should change it like this:
int[] a = new int[s];
string[] input = Console.ReadLine().Split(' ');
for (i = 0; i < s; i++)
{
a[i] = Int32.Parse(input[i]);
}
You need to read the input only once btw.
Like #loneshark99 said it would be even better to use TryParse(). Since that returns a boolean, you can check if the input are indeed integers. If you just use Parse and they are not integers, it would throw an exception.
Code with TryParse():
int[] a = new int[s];
string[] input = Console.ReadLine().Split(' ');
for (i = 0; i < s; i++)
{
if (Int32.TryParse(input[i], out a[i]))
{
//successfully parsed
}
}
The if-statement is not necessary but it's just to point out how you could use the TryParse.
We can take the input as string first
string[] array_temp = Console.ReadLine().Split(' ');
and then convert the array into Int
int[] array = Array.ConvertAll(array_temp,Int32.Parse);

c# switch all letters in a string for a different pre-chosen letter

Whilst working on a simple project I was trying to come up with a very basic cryptographic system which will allow me to switch letters in a message to another pre-chosen letter. So far I have tried a few ways but have so far been unsuccessful in my attempts. (*NOTE: This is not for anything other then learning the basics of c# so randomness and security is not important in this case, I simply want to turn one letter into another for the sake of learning how to do it)
so first I started by defining some strings such as this
string a = "a";
string b = "b";
string c = "d";
..... //continues to string z = "z"
next I tried to create a new string based on the values that have been input in to a textbox called PlainTextBox and place them inside a separate textbox called ChangedTextBox. this code is triggered with a button click event.
string str = PlainTextBox.Text;
char[] array = str.ToCharArray();
array[int.Parse(a)] = 'x';
array[int.Parse(b)] = 'y';
array[int.Parse(c)] = 'z';
.......// continues to (z)
str = new string(array);
ChangedTextBox.Text = str;
but this code throws an exception because the input is not a valid integer. the basic Idea is that if the user types "abc" in the PlainTextBox and pushes a button, the ChangedTextBox should show "xyz" but should be inclusive of the whole text in PlainTextBox, switching every letter in the message to its chosen counterpart.
Besides the error I receive, this code seems very cumbersome and inefficient.
Is there a faster way to achieve this result?
Just for completeness I will also include information, that what you are doing is called Caesar cipher
You could define yourself a proper Dictionary
var mapping = new Dictionary<char, char>()
{
{ 'a', 'x' },
{ 'b', 'y' },
{ 'c', 'z' }
// other letters
}
in which you would assign every original letter the letter it should be converted to. Then you could use this dictionary
ChangedTextBox.Text = new string(PlainTextBox.Text.Select(letter => mapping[letter].ToArray());
You've chosen wrong collection type (array) for mapping; dictionary is much more convenient
private static Dictionary<char, char> m_Mapping = new Dictionary<char, char>() {
{'a', 'x'}, // a -> x
{'b', 'y'}, // b -> y
...
};
Then implement the encoding
// I'd rather used Linq
private static String Encode(String value) {
// Simplest: we don't check if the actual character can be mapped
return String.Concat(value.Select(c => m_Mapping[c]));
}
But your (amended) implementation is good enough:
private static String Encode(string str) {
char[] array = str.ToCharArray();
for (int i = 0; i < array.Length; ++i) {
// Simplest: we don't check if the actual character can be mapped
array[i] = m_Mapping[array[i]];
}
return new string(array);
}
Finally, add up UI:
ChangedTextBox.Text = Encode(PlainTextBox.Text);
Edit: in general case, when m_Mapping doesn't contain records for some characters (e.g. for new line \n) and so we want to preserve these characters intact we can't use direct m_Mapping[...] but should implement, say, EncodeChar.
private static char EncodeChar(char value) {
char result;
if (m_Mapping.TryGetValue(value, out result))
return result;
else
return value;
}
And put EncodeChar(...) instead of m_Mapping[...]
private static String Encode(String value) {
return String.Concat(value.Select(EncodeChar(c)));
}
Your version
private static String Encode(string str) {
char[] array = str.ToCharArray();
for (int i = 0; i < array.Length; ++i) {
array[i] = EncodeChar(array[i]);
return new string(array);
}
Probably the best solution is using a Dictionary, as other answers had said. But if I understand what you want, you want to just change one letter by that letter plus an offset in a kind of "circular" way. This solution would do something like that (with "abcd" as input it would return "xyza"):
string input = "abcd";
char startChar = 'x';
char lastChar = 'z';
char firstChar = 'a';
byte[] asciiBytes=Encoding.ASCII.GetBytes(input);
byte[] encriptedByteArray = new byte[asciiBytes.Length];
int val = (int)startChar-(int)firstChar;
int i = 0;
foreach(byte b in asciiBytes)
{
var a=b + val;
if (a>(int)lastChar)
{
a = firstChar+(a-lastChar)-1;
}
encriptedByteArray[i] = (byte)a;
i++;
}
string encriptedArray = System.Text.Encoding.UTF8.GetString(encriptedByteArray);
With this solution you can change the offsety easily (changing startChar). It has room for improvement though, for example it only works on lower letters from a-z, it could be changed to be more extensive.
int.Parse(a)
will of course throw InvalidCastException because a is a string as you've defined it
string a = "a";

Reverse a foreach loop action

I want to convert/find each of my string characters to (int) and reverse this operation.
I manage to do the first part,but the seconds one is giving me some problems.
string input;
string encrypt = ""; string decrypt = "";
input = textBox.Text;
foreach (char c in input)
{
int x = (int)c;
string s = x.ToString();
encrypt += s;
}
MessageBox.Show(encrypt);
foreach (int i in encrypt)
{
char c = (char)i;
string s = c.ToString();
decrypt += c;
}
MessageBox.Show(decrypt);
Thanks!
Here is a fixed program according to my advise above
string encrypt = ""; string decrypt = "";
string input = Console.ReadLine();
var length = input.Length;
int[] converted = new int[length];
for (int index = 0; index < length; index++)
{
int x = input[index];
string s = x.ToString();
encrypt += s;
converted[index] = x;
}
Console.WriteLine(encrypt);
for (int index = 0; index < converted.Length; index++)
{
char c = (char)converted[index];
string s = c.ToString();
decrypt += s;
}
Console.WriteLine(decrypt);
This will not work as is, because you're adding numbers to a string with no padding.
Let's assume the first three letter's values are '1','2','3', you'll have a string with "123".
Now, if you know each letter is 1 int length, you're good, but what happens if 12 is valid? and 23?
This might not be a "real" issues in your case because the values will probably be all 2 ints long, but it's very lacking (unless it's homework, in which case, oh well ...)
The ascii values for the alphabet will go from 65 for A to 122 z.
You can either pad them (say 3 chars per number, so 065 for A, and so on), delimit them (have ".", and split the string on that), use an array (like shahar's suggestion), lists, etc etc ...
In Your scenario, encryption may give output as you expected but its hard to decrypt the encrypted text using such mechanism. so I just do some customization on your code and make it workable here.
i suggest a similar one here:
string input;
string encrypt = ""; string decrypt = "";
int charCount = 0;
input = "textBox.Text";
foreach (char c in input)
{
int x = (int)c;
string s = x.ToString("000");
encrypt += s;
charCount++;
}
// MessageBox.Show(encrypt);
while (encrypt.Length > 0)
{
int item = Int32.Parse(encrypt.Substring(0, 3));
encrypt = encrypt.Substring(3);
char c = (char)item;
string s = c.ToString();
decrypt += c;
}
Reason for your code is not working:
You have declared encrypt as string and iterate through each integer in that string value, it is quiet not possible.
if you make that loop to iterate through each characters in that string value again it gives confusion. as :
lets take S as your input. its equivalent int value is 114 so if you make a looping means it will give 1,1,4, you will not get s back from it.

How do I split a word's letters into an Array in C#?

How do I split a string into an array of characters in C#?
Example String word used is "robot".
The program should print out:
r
o
b
o
t
The orginal code snippet:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Diagnostics;
using System.IO;
using System.Text.RegularExpressions;
namespace Testing
{
class Program
{
static void Main(string[] args)
{
String word = "robot";
String[] token = word.Split(); // Something should be placed into the () to
//print letter by letter??
foreach (String r in token)
{
Console.WriteLine(r);
}
}
}
}
How can the codes be correctly implemented?
Why not this?
public void WriteLetters(string s)
{
foreach (char c in s)
{
Console.WriteLine(c);
}
}
If you really want to see it in an explicit character array, do the following:
string s = "robot";
char[] charArray = s.ToCharArray();
If you then want to print that out (1 per line), do the following:
for (int i = 0; i < charArray.Length; i++)
{
Console.WriteLine(charArray[i]);
}
I'm not really sure what you're trying to do, so I may be way off base.
If by tokenize, you mean store the characters in an array, you already have that in a String object1.
1 Not actually true, because String uses an indexer to iterate through the character values, whereas in C/C++, a string is actually an array of characters. For our purposes, we can treat a string as if it is an array of characters
The class String implements IEnumerable<char> and therefore to run through the letters of a string, you can just grab an IEnumerator<char> and process the chars one at a time. One way to do this is using a foreach:
foreach(char c in "robot") {
Console.WriteLine(c);
}
If you need each char in an array you can just use String.ToCharArray:
char[] letters = "robot".ToCharArray();
Do you mean something like this?
foreach(var alpha in myString.Where(c => Char.IsLetter(c)))
{
Console.WriteLine(alpha);
}
You can using ToArray() method to return the char array.
string word = "robot";
char[] array = word.ToArray();
You are trying to do too much.
Try this:
String word = "robot";
foreach (char letter in word)
{
Console.WriteLine(letter);
}
Edit:
To split the string into character array, without a loop, you can do this: word.ToCharArray()
Seems everyone wants to convert a String into an Array of Chars.
How about
for(int i = 0; i < tmpString.Length; i++)
Console.WriteLine(tmpString[i]);
Now you have the speed of a char array without the extra memory of making a copy.
edit: A String is an array of chars internally, there just isn't a way to change their values because String are immutable. But you can read from that char array. String = Read-Only char array.
I can't think of any reason to convert a String into a Char[] unless you wanted to "edit" the string.
long lTicks;
char[] tmpChar = { 'a', 'b', 'c', 'd', 'e' };
String tmpString = "abcde";
char chRead;
lTicks = DateTime.Now.Ticks;
for (int i = 0; i < 100000000; i++)
chRead = tmpChar[i%5];
Console.WriteLine(((DateTime.Now.Ticks - lTicks) / 10000).ToString());
lTicks = DateTime.Now.Ticks;
for (int i = 0; i < 100000000; i++)
chRead = tmpChar[i % 5];
Console.WriteLine(((DateTime.Now.Ticks - lTicks) / 10000).ToString());
lTicks = DateTime.Now.Ticks;
for (int i = 0; i < 100000000; i++)
chRead = tmpString[i%5];
Console.WriteLine(((DateTime.Now.Ticks - lTicks) / 10000).ToString());
lTicks = DateTime.Now.Ticks;
for (int i = 0; i < 100000000; i++)
chRead = tmpString[i % 5];
Console.WriteLine(((DateTime.Now.Ticks - lTicks) / 10000).ToString());
Console.ReadLine();
Kind of funny, the String is actually consistently faster than the Char[]. I ran each twice to make sure there wasn't a load time issue affecting the results. Compiled as Release with optimizations. Char[] was ~1950ms and String ~1850ms every run for me.

Categories

Resources