I have Linq query where I am trying to write subquery to set the value of item, I am encountering with error saying
{ORA-00907: missing right parenthesis
}, Please let me know the right syntax to make it work
var lst = (
from cr in dbContext.Company
orderby cr.COMPANY_KEY
select new CompanyDto()
{
CompanyKey = cr.CompanyKey,
CompanyCode = (from rc in dbContext.COMPANY_PORTFOLIOS where rc.PORTFOLIO == cr.P_PORTFOLIO select rc.COMPANY_CODE).FirstOrDefault()
}
);
var d = st.Skip(pageIndex).Take(pageSize).ToList();
Even the below piece of code is not working
var lst = (
from cr in dbContext.Company
orderby cr.COMPANY_KEY
select new CompanyDto()
{
CompanyKey = cr.CompanyKey,
CompanyCode = (from rc in dbContext.COMPANY_PORTFOLIOS where rc.PORTFOLIO == cr.P_PORTFOLIO select rc.COMPANY_CODE).Single()
}
);
var d = st.Skip(pageIndex).Take(pageSize).ToList();
I think you can just use a Join to achieve what you are looking to do:
var lst = (
from cr in dbContext.Company
orderby cr.COMPANY_KEY
join rc in dbContext.COMPANY_PORTFOLIOS on cr.PORTFOLIO equals rc.P_PORTFOLIO into myJoin
from rc in myJoin.DefaultIfEmpty()
select new CompanyDto()
{
CompanyKey = cr.CompanyKey,
CompanyCode = rc.COMPANY_CODE
}
);
var d = lst.Skip(pageIndex).Take(pageSize).ToList();
If the above still gives Oracle errors, put a breakpoint at the last line and get the SQL the linq generates. You can then paste this into something like Oracle SQL Developer and run the query, which may give you a more informative error message and allow you to track down the issue.
Related
Can anyone help me to make below query as linq
SELECT E.Cosem_Object, COALESCE(A.Explanation, 'Not Available' ) As
Explanation ,A.Unit, E.Reading , E.Unit, E.Meter_Date, E.Meter_Time from
ENERGY_PROFILE E LEFT OUTER JOIN ALL_COSEM_OBJECTS A on
(SUBSTRING(E.Cosem_Object,0,CHARINDEX('*',E.Cosem_Object + '*',0))) = A.Short_Cosem_Object
Updated:
I try
var query = from o in ENERGY_PROFILE
join e in ALL_COSEM_OBJECTS
on o.Short_Cosem_Object equals e.Short_Cosem_Object
select new {
o.Short_Cosem_Object, o.READING, e.EXPLANATION, e.UNIT
};
I need to add below line
SUBSTRING(E.Cosem_Object,0,CHARINDEX('*',E.Cosem_Object + '*',0)) in linq query
here's the exact conversion of your SQL query into LINQ, though I'm not sure if it's exactly what you are expecting since the lack of a sample and expected result:
var set = from E in ENERGY_PROFILE
join A in ALL_COSEM_OBJECTS
on E.Cosem_Object.Substring(0, (E.Cosem_Object + "*").IndexOf('*')) equals A.Short_Cosem_Object
into joinedTb
from c in joinedTb.DefaultIfEmpty()
select new
{
E.Cosem_Object,
Explanation = c.Explanation ?? "Not Available",
c.Unit,
E.Reading,
Unit2 = E.Unit,
E.Meter_Date,
E.Meter_Time
};
I am able to write this code for a Web Api. In this code i have written tow queries and combined both in a way that comments and follower data should be merged (not combined) with respect to time based on ctime and startedfollowing. If a user has a new comment, the comment should come first and if the follower is first, the follower data should come first.
public IQueryable<Object> GetCommentsandFollowActivityCommnets()
{
var combo1 = from c in db.comments
join p in db.picturedetails on c.targetpictureid equals p.idpictures
join u in db.users on c.iduser equals u.iduser
select new TCommentDTO
{
idcomments=c.idcomments,
comment1 = c.comment1,
targetpictureid = c.targetpictureid,
ctime = c.ctime,
iduofpic=p.iduser,
iduofcommentor=c.iduser,
profilepicofcommentor=u.profilepic,
usernameofcommentor=u.username,
picFilename=p.picFilename,
picTitle=p.picTitle
};
var combo2= from f in db.followers
join u in db.users on f.iduser equals u.iduser
select new TfollowerDTO
{
idfollowers=f.idfollowers,
iduser=f.iduser,
targetiduser=f.targetiduser,
startedfollowing=f.startedfollowing,
unoffollower=u.username,
ppoffollower=u.profilepic,
status=u.status
};
var result1 = from c in combo1
select new UserTimeLineDTO
{ SortKey = c.ctime, Member =c};
var result2 = from c in combo2
select new UserTimeLineDTO{ SortKey = c.startedfollowing, Member = c };
var result = result1.Concat(result2).OrderBy(x =>x.SortKey).Select(x => x.Member);
return result;
}
The code is not giving any compile time error. It runs fine in compiler, but on run time i am getting an exception:
DbUnionAllExpression requires arguments with compatible collection ResultTypes.
How to remove this exception?
As a workaround, I would try to evaluate the last expression in memory:
var result1 = (from c in combo1
select new UserTimeLineDTO
{ SortKey = c.ctime, Member =c}).ToList();
var result2 = (from c in combo2
select new UserTimeLineDTO{ SortKey = c.startedfollowing, Member = c }).ToList();
var result = result1.Concat(result2).OrderBy(x =>x.SortKey).Select(x => x.Member);
The union should now succeed, as well as ordering and the final projection.
Using Linqpad to work out my query, get the above error on:
(from bp in basepay_records
select new { empID = bp.Prep_emp, loc = bp.Prep_loc }).Union
(
from ass in emp_assignments
select new { empID = ass.Prea_emp, loc = ass.Prea_loc }
)
I have tried it with and without the paren on the first query, no diff. This union is part of a larger query, and this will end up sitting in a subquery that is used in a join, so I can't do the usual, though I did it test it as a stand alone query and it failed, saying no definition for Union:
var q1 = from bp in basepay_records select new { empID = bp.Prep_emp, loc = bp.Prep_loc };
var q2 = from ass in emp_assignments select new { empID = ass.Prea_emp, loc = ass.Prea_loc };
q1.Union (q2).Dump ("Union");
I confirmed that all the datatypes match.
Full error message is:
Cannot execute text selection: 'System.Linq.IQueryable' does not contain a definition for 'Union' and the best extension method overload 'System.Linq.ParallelEnumerable.Union(System.Linq.ParallelQuery, System.Collections.Generic.IEnumerable)' has some invalid arguments
Instance argument: cannot convert from 'System.Linq.IQueryable' to 'System.Linq.ParallelQuery'
I have it working now. I had to split it into 2 queries, which seems stupid, but there you go. Let me know if you have a beter way:
var q1 = from mstr in emp_master_records
join loctab in
(
from bp in basepay_records
select new { empID = bp.Prep_emp, loc = bp.Prep_loc }
)
on mstr.Prem_emp equals loctab.empID
where mstr.Prem_email.StartsWith("TEST_USER")
select loctab.loc;
var q2 = from mstr in emp_master_records
join loctab in
(
from ass in emp_assignments
select new { empID = ass.Prea_emp, loc = ass.Prea_loc }
)
on mstr.Prem_emp equals loctab.empID
where mstr.Prem_email.StartsWith("GREGORY_RANDALL")
select loctab.loc;
q1.Union(q2).Dump ("Union");
I am having following query in sql :
SELECT [definition],[pos]
FROM [WordNet].[dbo].[synsets]
where synsetid in(SELECT [synsetid] FROM [WordNet].[dbo].[senses]
where wordid = (select [wordid]FROM [WordNet].[dbo].[words]
where lemma = 'searchString'))
I had tried this for sql to linq :
long x = 0;
if (!String.IsNullOrEmpty(searchString))
{
var word = from w in db.words
where w.lemma == searchString
select w.wordId;
x = word.First();
var sence = from s in db.senses
where (s.senseId == x)
select s;
var synset = from syn in db.synsets
where sence.Contains(syn.synsetId)
select syn;
But I am getting following error at sence.Contains()
Error1:Instance argument: cannot convert from
'System.Linq.IQueryable<WordNetFinal.Models.sense>' to
'System.Linq.ParallelQuery<int>'
Below code:
var sence = from s in db.senses
where (s.senseId == x)
select s;
Returns object of type: WordNetFinal.Models.sense, but in where sence.Contains(syn.synsetId) you are trying to search in it syn.synsetId which is an integer.
So you should change above code to:
var sence = from s in db.senses
where (s.senseId == x)
select s.senseId;
x seems to be of Word type, which is not the type of Id (probably int or long).
You're comparing an entire sense row with a synsetId, which is not correct. You're also splitting the original query into two separate queries by using First() which triggers an evaluation of the expression so far. If you can live with not returning an SQL error if there are duplicates in words, you can write the query as something like this;
if (!String.IsNullOrEmpty(searchString))
{
var wordIds = from word in db.words
where word.lemma == searchString
select word.wordId;
var synsetIds = from sense in db.senses
where wordIds.Contains(sense.wordId)
select sense.synsetId;
var result = (from synset in db.synsets
where synsetIds.Contains(synset.synsetId)
select new {synset.definition, synset.pos}).ToList();
}
The ToList() triggering the evaluation once for the entire query.
You could also just do it using a simpler join;
var result = (from synset in db.synsets
join sense in db.senses on synset.synsetId equals sense.synsetId
join word in db.words on sense.wordId equals word.wordId
select new {synset.definition, synset.pos}).ToList();
I have this original SQL that I need to rewrite in LINQ :
SELECT
luProfiles.luProfileID,
luProfiles.ProfileName,
NoOfRights = (SELECT Count(pkProfileRightsID) FROM tblProfileRights WHERE fkProfileID = luProfileID)
FROM luProfiles
WHERE luProfiles.ProfileName LIKE ...
I have done most of it in LINQ, but I am not sure how to add the NoOfRights part to my LINQ. This is what I have done so far :
return from p in _database.LuProfiles
where p.ProfileName.ToLower().StartsWith(strProfile.ToLower())
select p;
Can anybody tell me the right syntax to include the NoOfRights part in my LINQ?
from p in _database.LuProfiles
let NoOfRights = (from r in database.tblProfileRights
where r.fkProfileID == p.luProfileID
select r).Count()
where p.ProfileName.ToLower().StartsWith(strProfile.ToLower())
select new
{
p.luProfileID,
p.ProfileName,
NoOfRights
};
If you are using LINQ-to-SQL or EF, and you have an FK set up, you should have a navigational property ProfileRights. Tn that case, you can query this way:
from p in _database.LuProfiles
where p.ProfileName.ToLower().StartsWith(strProfile.ToLower())
select new
{
p.ProfileId,
p.ProfileName,
NoOfRights = p.ProfileRights.Count()
};
I think this would help you out:
from l in luProfiles
where l.ProfileName.Contains(something)
select new
{
l.luProfileID,
l.ProfileName,
noOfRights = tblProfileRights.Count(t => t.fkProfileID == l.luProfileID)
}
I would recommend you to change SQL first to something like this:
SELECT
luProfiles.luProfileID,
luProfiles.ProfileName,
NoOfRights = COUNT(pkProfileRightsID)
FROM luProfiles
LEFT JOIN tblProfileRights ON fkProfileID = luProfileID
WHERE luProfiles.ProfileName like ...
GROUP BY luProfiles.luProfileID, luProfiles.ProfileName
So this can easily be transformed to LINQ:
return from p in _database.LuProfiles
join o in p.Profiles on p.luProfileID equals o.fkProfileID
group p by new { p.luProfileID, p.ProfileName } into g
select new { g.Key.luProfileID, g.Key.ProfileName , g.Count() }
(not tested, so do it yourself)