0

This function always returns null. sString is a class with a string "Name" and string "Value" values. Don't ask why I'm not using a regular string-- it's complicated. here's my function:

static string Get_sString(string VarName, ref List<sString> VarList)
{
    foreach (sString TestsString in VarList)
    {
        if (TestsString.Name == VarName)
        {
            return TestsString.Name;
        }
    }
    return null;
}

It's supposed to return the instance with the same Name value as VarName, and it works, except for the if statement always is false. I can't figure out why. I actually have an almost identical class called sDecimal, where the only difference is the Value property is a decimal, not a string. The Get_sDecimal() works perfectly fine with that, and the only difference between Get_sDecimal() and Get_sString() are that one tests sDecimal and one tests sString. Thanks!

EDIT: Here's sString Class.

class sString
{
    public string Name;
    public string Value;

    /// <summary>
    /// String Value variables that may have the same name.
    /// </summary>
    /// <param name="n">Internal name of variable.</param>
    /// <param name="v">Value of variable.</param>
    public sString(string n, string v)
    {
        Name = n;                    
        Value = v;                    
    }
}

EDIT: Here's some output code (and output) to clear things up.

static string Get_sString(string VarName, ref List<sString> VarList)
        {
            foreach (sString TestsString in VarList)
            {
                Console.WriteLine("Looking for: " + VarName);
                Console.WriteLine("Comparing with: " + TestsString.Name);
                if (TestsString.Name == VarName)
                {
                    Console.WriteLine("Match!");
                    return TestsString.Name;
                }
            }
            return null;
        }

Here's the output:

Looking for: Q
Comparing with: Q

EDIT: I added a couple more variables to the list. Here's the new output:

Looking for: Q
Comparing with: Q
Looking for: Q
Comparing with: Z
Looking for: Q
Comparing with: VariableX

Still no Match.

cubician
  • 19
  • 1
  • 6
  • 7
    Can I ask why you are not using a regular Dictionary instead? – Thilo Jun 01 '13 at 04:28
  • 1
    When you break in the code and you manually check VarList, does it actually contain the string you are searching for (remember `==` is case senstive)? – Scott Chamberlain Jun 01 '13 at 04:28
  • Yes, it does. I did a check where it printed both the VarName and TestsString.Name on the screen, and both were Identical. It still returned null. – cubician Jun 01 '13 at 04:33
  • 4
    Unrelated to the question, but that `ref` does nothing useful here: that should be removed IMO – Marc Gravell Jun 01 '13 at 04:33
  • did you try using .Equals() instead of == – a_schimpf Jun 01 '13 at 04:34
  • Can you update the question with `sString` class and how you call `Get_sString` and sample inputs – Damith Jun 01 '13 at 04:34
  • What is .Name typed as? Is that a `string`? What are the inputs here: is there actually a match expected? – Marc Gravell Jun 01 '13 at 04:35
  • Yes, I have. Still returns null. – cubician Jun 01 '13 at 04:35
  • I'm editing with a sString.Class. – cubician Jun 01 '13 at 04:36
  • the ref is a reference to a list in a seperate class. – cubician Jun 01 '13 at 04:38
  • 2
    With your update, the most likely answer is that there **simply isn't a match**. Can you show some inputs where this is failing unexpectedly? – Marc Gravell Jun 01 '13 at 04:38
  • 1
    @a_schimpf You're thinking of Java, this is C# – Patashu Jun 01 '13 at 04:39
  • @cubican if your "the ref is..." relates to the `ref`: that is irrelevant: again - the `ref` here doesn't help you. It isn't the cause of the problem, but it simply isn't needed. – Marc Gravell Jun 01 '13 at 04:39
  • @cubician and I am still curious about Thilio's original question to you, Why not use a `Dictionary` instead? – Scott Chamberlain Jun 01 '13 at 04:41
  • `TestsString.Name.Trim().Equals(VarName.Trim(), StringComparison.InvariantCultureIgnoreCase)` to be sure there is no case mismatch or white spaces – Corak Jun 01 '13 at 04:46
  • @cubician - I took your posted code and wrote a console app to test it, and the function returned the match. Are you sure there's not a typo or something else going on? Can you post some sample code where you use the function, and how you populate the List? – Tim Jun 01 '13 at 04:46
  • Here's how I'm calling the function, I may be doing it wrong (calling my own function wrong, hardihar XD) : string svalue = Get_sString(name, ref StringVar); where StringVar is a List. – cubician Jun 01 '13 at 04:49
  • 1
    Re your example: can you make that: `Console.WriteLine("Looking for: \"" + VarName + "\"");` (and likewise for the other value) - my suspicion is that there is some whitespace involved here - and the two values are not, in fact, equal. `"Q"` != `"Q "`. Of course, it could also be some invisible control/unicode character. – Marc Gravell Jun 01 '13 at 04:51
  • Why are you using ref again while calling the function cubician? That might be the cause. – Jay Patel Jun 01 '13 at 04:58
  • @Jay the `ref` doesn't cause any *actual harm* here; it just makes it bizarre – Marc Gravell Jun 01 '13 at 05:06
  • @MarcGravell haha I got confused by the use of two ref. – Jay Patel Jun 01 '13 at 05:15
  • I added a .Trim(), still doesn't work. Also had it return Value, not Name. Just ignore the ref for now. – cubician Jun 01 '13 at 05:26
  • I dunno... I'll just rewrite sString and Get_sString. Whatever. – cubician Jun 01 '13 at 05:30
  • @cubician Can you write minimal Console application to recreate this issue? please update the question with that. – Damith Jun 01 '13 at 05:48
  • actually, it was some sort of whitespace. I was putting the trim before some other function, so it wasn't trimming it all off. I was having it replace "[str]" with "", but I changed it to replace "[str] " with "". Thanks... what a stupid mistake. :D **Thanks!** – cubician Jun 01 '13 at 17:27

3 Answers3

6

The code fundamentally works:

var list = new List<sString>
{
    new sString("foo", "123"),
    new sString("bar", "456")
};
var s = Get_sString("foo", ref list);
// = "foo", not null

Don't get me wrong - I'd change every line of it. But it doesn't always return null.

Brief problem list:

  • public fields
  • unnecessary ref
  • could just use Dictionary<string,string>
  • horrible names
  • I wonder if you should be returning .Value rather than .Name
Marc Gravell
  • 1,026,079
  • 266
  • 2,566
  • 2,900
2

You do realize that you have basically re-implemented LINQ:

return VarList.FirstOrDefault(x=> x.Name == VarName);

Also your sString class could just be a KeyValuePair<string,string>

UPDATE

Actually, you said:

It's supposed to return the instance with the same Name value as VarName

But it doesn't return an sString instance. Instead, it returns TestsString.Name - which is the same string you started with, but only if it's in the list. So basically, this is a complicated "contains" check.

Matt Johnson-Pint
  • 230,703
  • 74
  • 448
  • 575
  • you can't quite use *just* `FirstOrDefault` here; the return value needs to be the `.Name`, not the `sString`. And there's nothing wrong with a good honest `foreach` loop ;p – Marc Gravell Jun 01 '13 at 04:56
  • @MarcGravell - Actually, I see now why I made that mistake. Read his text right after the code. I'll update... – Matt Johnson-Pint Jun 01 '13 at 05:00
  • 1
    yeah, it could be `return VarList.Any(x => x.Name == VarName) ? VarName : null;` - which is a very odd test to run – Marc Gravell Jun 01 '13 at 05:03
1

You should use String.Equals instead of == operator.

== operator does not always work. you can find samples in the thread Are string.Equals() and == operator really same?.

Community
  • 1
  • 1
Suresh Kumar Veluswamy
  • 4,193
  • 2
  • 20
  • 35
  • 1
    Since the types are known statically as `==`, there is no good reason to use `Equals` here, and a very good reason not to (`==` avoids issues with `null`) - and a mediocre reason not to (`==` avoids an unnecessary virtual dispatch). Basically, if you know the data types, `==` is usually preferable in .NET – Marc Gravell Jun 01 '13 at 05:18