Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 9 years ago.
Improve this question
Hello everyone I recently started using C# with unity for game development and things are coming along quite well. The problem I'm having isn't with the functionality of my code but it's more in the style of coding it. I studied ANSI C for 4 years through high school so now as I jump to C# I really can't wrap my head around using pre-made classes (besides ones that I used in C which were called libraries). At this point my code looks very similar to C with some effort at implementing OOP principles. I'm afraid that if another C# developer looked at this code, they would call it sloppy and unreadable (my C code isn't really the most elegant anyway as you'll see). I've been a lone wolf trying my best to teach myself in hopes of becoming an indie developer. so I don't have experience with team based assignments. Here's a sample of a method in my application:
public void create_item(string item_name,char L_M_H,int item_cat)//function not finshed july 13th 2013 8:07pm other fuel items need to be finished. due july 14th 10:00pm
{
int i = 0;
if(item_cat == FUEL)
{
print("item_cat is fuel");
if(L_M_H == L)
{
for(i = 0;i < 5;i++)
{//increments if fuel index has a value
if(l_fuel[i] != null)
continue;
if(l_fuel[i] == null)
{
l_fuel[i] = item_name;
Debug.Log (string.Format("Low Class Fuel: {0} Created",l_fuel[i]));
break;
}
}
}
if(L_M_H == M)
{
for(i = 0; i < 5; i++)
{
if(m_fuel[i] != null)
{
continue;
}
if(m_fuel[i] == null)
{
m_fuel[i] = item_name;
}
}
}
}
}
I'm sure there's a better way to perform functions like this in C#, however is it worth it to stop development to use classes and C# specific types like List to perform these tasks? I'm very interested in getting opinions from seasoned programmers as I'm a total noob in C# and OOP.
Yes, your code is sloppy and unreadable.
1 - Respect the C# Naming Conventions:
Your method and member names should be ProperCased, so it's public void CreateItem()
2 - Do not use primitive types where they don't belong.
Both parameters char L_M_H and int item_cat seem to be used here to emulate Enums.
3 - As other have mentioned in comments, your m_fuel and l_fuel things look strange. Make sure you create a proper data model to represent your data.
4 - Do not use for to iterate collections. Use foreach or LINQ.
public interface IFuelUpdater {
void UpdateFuelItemContainerSlots(string[] container, string itemName);
}
public class MediumOrLowFuelUpdater : IFuelUpdater {
public void UpdateFuelItemContainerSlots(string[] container, string itemName){
for(i = 0; i < container.Length; i++)
{
if(container[i] == null)
{
container[i] = item_name;
}
}
}
}
// elsewhere
IFuelUpdater updater = new MediumOrLowFuelUpdater();
string[] mediumContainer = new string[6];
string[] lowContainer = new string[6];
updater.UpdateFuelItemSlots(mediumContainer, "*Name Goes Here*");
updater.UpdateFuelItemSlots(lowContainer, "*Low Name Goes Here*");
This is how your code might look if it were made more OOP. This example is pretty nonsensical. I imagine that you really only have only one logical "fuel" array but perhaps you are forced to have two in your code because of some improper design elsewhere or some pre-optimization.
Related
Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 2 years ago.
Improve this question
I solved this codility test with the following code:
private static int lesson2_1(int[] A) {
if (!Isvalid(A))
{
return -1;
}
List<int> d = A.Distinct().ToList();
foreach (var item in d)
{
var q = from one in A where one == item select one;
if (q.Count() == 1)
{
return item;
}
}
return -1;
}
private static bool Isvalid(int[] a)
{
if (a.Length == 0)
{
return false;
}
return true;
}
These are the results:
I do not know how to approach this, since I have not learned yet about complexity. Can someone please guide me to the right approach to this issue?
Many thanks
My advice - don't reinvent the wheel. .Net has a lot built into it. Chances are unless you have specialist requirements Microsoft will be able to implement it better than you. The following gets a 100% score:
using System;
using System.Linq;
class Solution {
public int solution(int[] A) {
return A.GroupBy(a => a).First(a => a.Count() %2 == 1).Key;
}
}
There are a few issues with your solution.
1) You aren't following the test spec. It states
all but one of the values in A occur an even number of times.
That means that the number you are looking for could occur, 3,5,7,etc. times - you are just checking for 1.
2) The time complexity of your solution is poor. You are looping through every item and doing a search for each item within every loop. This isn't necessary if you think about it. You will have to go through every item in the list but if you process it as you go along you effectively only have to go through each item once and then the buckets of each item once.
Closed. This question needs debugging details. It is not currently accepting answers.
Edit the question to include desired behavior, a specific problem or error, and the shortest code necessary to reproduce the problem. This will help others answer the question.
Closed 2 years ago.
Improve this question
I am new to C# but I have learned Java for a year and I found C# almost similar. I am trying to make a program where the output is like this
My
My Name
My Name Is
My Name Is Ahan
and the program I have written is this
class Program
{
static void Main(string[] args)
{
string str1 = "My Name Is Ahan";
int i = 0 , length = str1.Length;
Console.WriteLine(length);
for(; i<length; i++ )
{
char ch = str1[i];
if (ch == ' ')
{
int catchnum = str1.IndexOf(ch);
string displayValue = str1.Substring(0, catchnum);
Console.WriteLine(displayValue);
}
else;
}
Console.ReadLine();
}
}
Something like this?
static void Main(string[] args)
{
string str1 = "My Name Is Ahan";
string[] words = str1.Split(' ');
for (int i=0;i<words.Length;i++)
{
var selectedWords = words.Take(i + 1);
Console.Write($"{string.Join(" ", selectedWords)} ");
}
}
I think your problem is here:
int catchnum = str1.IndexOf(ch);
Within the loop you're always finding the index of the first space. You already have the index of the current space when you find it, so you could just do:
if (ch == ' ')
{
string displayValue = str1.Substring(0, i);
Console.WriteLine(displayValue);
}
I would also note that C# and Java are extremely similar for these basic operations - the same code would behave identically in Java with only minor syntax differences. Certainly the code could be simpler by using some basic library functions (like string.Split and Linq) that would be different between the two platforms, but that's not the issue here.
In other words, your errors aren't due to translation between Java and C# - they're basic logic errors that would have manifested in any programming language.
Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 7 years ago.
Improve this question
Must be a simple question, and I'm again close to a nervous breakdown because I can't find it:
I have a multimensional List that I defined as an own class (Id, Title, Desc, Start, Length, URL) and that I filled in one function
hyperlist.Add(
new ListElement
{
Id = n,
Title = title,
Desc = desc,
Start = OffsetTotal,
Length = TagLength,
URL = LinkURL
});
I pass it to another function where I have to loop through it and compare each entry of the list to a parameter.
void BuildGList(List<ListElement> LinkList)
{
int startIndex = 5;
foreach (int Id in LinkList)
{
if(startIndex < Start)
{
....
}
}
}
I don't see how to address each single column and googling it I get the impression that nobody uses lists to do what I want here.
-update-
I am asked to clarify my question. Lucky enough it had been clear to the ones that answered it: I didn't know how to refer to a special parameter in a List. Now I know that you can do it with item.parameter.I'm really grateful for the help received in Stackoverflow but sometimes I get the impression that many of you experienced coders have little empathy and understanding for the problems a beginner faces and the effort it takes to google through a jungle of posts. Especially if you are a beginner and therefore sometimes miss the correct keywords. On this one I was busy for an hour and close to a breakdown as I knew I was catching really simple. If you know it then it's always easy. Cheers
You can use foreach like this:
foreach (ListElement item in LinkList)
{
if (item.Length < startIndex)
{
//Do something
}
}
You can filter the list using Linq e.g. to return an IEnumerable as the subset you could do:
private IEnumerable<ListElement> BuildGList(List<ListElement> linkList)
{
int startIndex = 5;
return linkList.Where(element => startIndex < element.Start);
}
You can use takewhile with a foreach if you want to use the list index:
foreach(var item in LinkList.TakeWhile((item, index) => index < startIndex))
{
//enter your code here
}
Also, if you want to compare with a element value inside the list, you can use where with the foreach:
foreach(var item in LinkList.Where(item => item.Start < startIndex))
{
//enter your code here
}
Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 7 years ago.
Improve this question
I never liked out and ref parameters.When I see them in action they give me a feeling that something is messy about the design.
I thought that the only exception was the so called TryXXX pattern that returns a boolean as the function result (whether everything was fine or something went wrong) and an out parameter for the real result, until I read this article today and It made me think if there's a better pattern to implement this kind of methods.
I thought that we could either have a function that returns more than one result(or as the article says a tuple)
Tuple<Exception,T> TryParseT(object obj)
or a function that accepts a callback function for success :
void TryParseT(object obj,Action<T> success)
The question is , which one is better from a functional design point of view ?
UPDATE :
To rephrase my question , I want to know which of these two functions more complies with Functional Programming principles and why ?
Essentially the problem is that to follow the functional programming approach you should always provide a return value for an input value. So the returning void route isn't the way to go. You need to return a value that can represent success (and hold the successful result) and failure (and hold no result).
The closest to that is where you have returned a Tuple which includes the exception. However you then don't have the 'infrastructure' to deal with the Tuple reliably once you've got it. So the code scaffolding around it will be repeated.
Take a look at this library language-ext. It deals with improving the out problem for TryParse using its implementation of Option<T>.
string inp = "123";
// Attempts to parse the value, uses 0 if it can't
int value1 = parseInt(inp).IfNone(0);
// Functional alternative to above
// Attempts to parse the value, uses 0 if it can't
int value2 = ifNone(parseInt(inp), 0);
// Attempts to parse the value and then pattern matches the result
int value3 = parseInt(inp).Match(
Some: x => x * 2,
None: () => 0
);
// Functional alternative to above
// Attempts to parse the value and then pattern matches the result
int value4 = match( parseInt(inp),
Some: x => x * 2,
None: () => 0
);
The library also allows you to just check that something is valid:
if( parseInt(inp) )
return 1;
else
return 0;
And allows for comparisons without actually extracting the value:
if( parseInt(inp) == 123 )
return 123;
else
return 0;
As well as logical operations:
var allValid = parseInt(x) && parseInt(y) && parseInt(z);
var someValid = parseInt(x) || parseInt(y) || parseInt(z);
And finally LINQ expressions which can often remove the need for if-then-else or matching:
var res = from x in parseInt(inp1)
from y in parseInt(inp2)
from z in parseInt(inp3)
select x + y + z;
It also has TryGetValue extensions for IDictionary, IReadOnlyDictionary, IImmutableDictionary and IImmutableSet that instead return Option<T> and can be used as above.
The most elegant method is
int Parse(string value)
The Tryxxxx methods only exist for an implementation detail named performance. If you are seeking elegance you can use the Parse method and handle any errors by failing fast.
You can instead return a tuple but this will cost an additional allocation on the heap since Tuple is a reference type.
A better solution in terms of performance (if you care) would be aKeyValuePair. But it hides (like tuple) the semantics behind generic data types which is not optimal for code clarity. A better way to signal failure than by defining some convention that the first bool of the tuple contains the failure state is by defining your own data type.
struct ParseResult<T>
{
public bool Success { get; private set; }
public T Value { get; private set; }
public ParseResult(T value, bool success):this()
{
Value = value;
Success = success;
}
}
class Program
{
static ParseResult<int> TryParse(string s)
{
int lret = 0;
if (int.TryParse(s, out lret))
{
return new ParseResult<int>(lret, true);
}
else
{
return new ParseResult<int>(lret, false);
}
}
static void Main(string[] args)
{
string test = "1";
var lret = TryParse(test);
if( lret.Success )
{
Console.WriteLine("{0}", lret.Value);
}
}
}
That approach is still quite efficient and spares you the out parameters at the cost of the allocation of a cheap container object.
Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 9 years ago.
Improve this question
By seeing this solution specified in Divide Foreach into threads sample
I tried to implement it with this code:
foreach (Object vo in arrreclist)
{
msg = String.Empty;
objprocess.GetType().GetMethod("ProcessRecord").Invoke(objprocess, new Object[] { vo });
status = (StatusInfo)objprocess.GetType().GetProperty("status").GetValue(objprocess, null);
if (status.errcode != 0)
{
lngfailedcnt++;
WriteErrorLog();
}
else
{
lngsuccesscnt++;
lngInstanceSuccCount++;
}
lngcnt++;
if ((lngcnt % 10) == 0)
{
if (instanceId == 0)
{
schldr.ModifyJobhistoryForUploadFileRecCnt(Runid, (int)lngTotreccnt, lngfailedcnt, (int)(lngfailedcnt + lngsuccesscnt));
}
else
{
schldr.ModifyJobhistoryForUploadFileRecCnt(Runid, 0, lngfailedcnt, (int)(lngfailedcnt + lngsuccesscnt));
}
status = schldr.status;
if (status.errcode != 0)
{
if (!String.IsNullOrEmpty(Errorlogfile))
WriteErrorLog();
holdInstance = true;
break;
}
//Get Job Status
//If job was terminated then Update Batch and Job history with status as STOPPED
intstatus = schedulersvc.GetJobStatus(Runid);
status = schedulersvc.status;
if (status.errcode != 0)
{
WriteErrorLog();
holdInstance = true;
break;
}
if (intstatus == 1) //STOPPED
{
holdInstance = true;
break;
}
lngcnt = 0;
}
}
And error message is coming for break statement:
cannot leave the body of anonymous method or lambda expression
My major task is to parallelize the following line:
objprocess.GetType().GetMethod("ProcessRecord").Invoke(objprocess, new Object[] { vo })
But other are dependents so how to implement?
First, parallelization often doesn't make sense in ASP.NET. If you have many users accessing your site, you usually care more about scalability (how many users can you serve at the same time), than raw performance for single user.
If that's not your case, parallelization might make sense for you.
Second, you're getting that error, because Parallel.ForEach() is not a loop (as far as the language is concerned). And breaking out of a lambda doesn't make any sense.
To break out of Parallel.ForEach(), you can use ParallelLoopState.Break() or ParallelLoopState.Stop() (read the documentation to find out which one of those do you actually want). To do this, you will need to use an overload of Parallel.ForEach() that gives you that ParallelLoopState.
Third, there is a good reason why Parallel.ForEach() doesn't support ArrayList: it's because you should never use it. If you really want a list of objects, use List<object> to make it clear that you really don't know the type. If you can't (or don't want to) change the ArrayList, you can use .Cast<object>() to make Parallel.ForEach() (and other methods that work with IEnumerable<T>) accept it.
Fourth, I think that parallelizing just the ProcessRecord doesn't make sense. It looks like status returns the status for the last ProcessRecord. And if you execute ProcessRecord in parallel, then it's not clear anymore which one is the last.
Also, you shouldn't think that some method is not thread-safe. You should know that. If you parallelize something that you don't know is thread-safe, you're likely to get hard to debug bugs later on.
Fifth, if you want to parallelize just the first part of a loop, I think the best option is PLINQ. Something like:
var intermediateResults = source.AsParallel().Select(x => Process(x));
foreach (var intermediateResult in intermediateResults)
{
// the rest of the loop
}