I am trying to join a table (db.Students) within this query to get firstname and lastname included in the query by joining on the StudentID. How do I do this? I've come up with about 50 queries that don't work and one that only gives me half of what I want. This is what I have so far that is working.
var gradeaverages = db.Grades
.Where(r => r.StudentID == r.StudentID)
.GroupBy(g => g.StudentID, r => r.Grades)
.Select(g => new
{
StudentID = g.Key,
Rating = g.Average()
});
var data = gradeaverages.ToList();
dataGridView1.DataSource = data;
It does have a foreign key. Here is the constraint:
CONSTRAINT [FK_Grades_Students] FOREIGN KEY ([StudentID]) REFERENCES [dbo].[Students] ([StudentID])
Here are my tables:
CREATE TABLE [dbo].[Grades] (
[GradeID] INT NOT NULL,
[StudentID] INT NOT NULL,
[Date] NCHAR (10) NULL,
[Grades] DECIMAL (18) NULL,
PRIMARY KEY CLUSTERED ([GradeID] ASC),
CONSTRAINT [FK_Grades_Students] FOREIGN KEY ([StudentID]) REFERENCES [dbo].[Students] ([StudentID])
CREATE TABLE [dbo].[Students] (
[StudentID] INT NOT NULL,
[First Name] NVARCHAR (40) NOT NULL,
[Last Name] NVARCHAR (40) NOT NULL,
[Phone] NVARCHAR (24) NULL,
CONSTRAINT [PK_Table] PRIMARY KEY CLUSTERED ([StudentID] ASC)
I'm looking for an out put of
StudentID FirstName LastName AverageGrade (according to StudentID I assume)
Actually there is not enough information about db structure, but I guess your query might look like this:
var data = db.Students.Include("Grades")
.Select(x => new
{
StudentId = x.StudentId,
Rate = x.Grades.Avg(y => y.Mark)
})
.ToList();
This .Where(r => r.StudentID == r.StudentID) is meaningless, because you compare some value with itself.
Or like this
var data = db.Grades
.GroupBy(x => x.StudentId)
.Select(x => new
{
StudentId = x.Key,
Rate = x.Avg(y => y.Mark)
})
.ToList();
Related
I am developing an mvc App using Code First Approach. I want to generate VarcharID Based on the Identity Column Value. I know How to Achieve this in SQL. I want to Know how can I write the following SQL Query in VoidUp() Method
SQL Query I want to Write
CREATE TABLE [dbo].[EmployeeMaster](
[ID] [int] IDENTITY(1,1) NOT NULL,
[PreFix] [varchar](50) NOT NULL,
[EmployeeNo] AS ([PreFix]+ RIGHT('0000000' + CAST(Id AS VARCHAR(7)), 7)) PERSISTED,
[EmployeeName] VARCHAR(50),
CONSTRAINT [PK_AutoInc] PRIMARY KEY ([ID] ASC)
)
My Code in Migration.cs Void Up method
CreateTable(
"dbo.Employees",
c => new
{
ID = c.Int(nullable: false, identity: true),
EmployeePrefix = c.String(),
EmployeeEmpNo = c.String(), // Want to Change stuff Here
EmployeeName = c.String(nullable: false),
})
.PrimaryKey(t => t.ID);
You can write the data you need in "Seed" method of "Configuration.cs" file. You can find an example here. Your code will look smth like this:
foreach (var entity in context.EmployeeMaster.Where(em => string.IsNullOrEmpty(em.EmployeeNo))
{
var idStr = "0000000" + entity.Id.ToString();
entity.EmployeeNo = entity.Prefix + idStr.SubString(idStr.Length - 7);
}
context.SaveChanges();
Hope it will help you.
I have a table that looks like this.
CREATE TABLE [dbo].[loginInfos]
(
[loginId] INT IDENTITY (1, 1) NOT NULL,
[username] VARCHAR (50) NULL,
[password] VARCHAR (50) NULL,
PRIMARY KEY CLUSTERED ([loginId] ASC)
);
I want to get the username and compare it with a input from a textbox. It will really be a huge help.
var MyDb = new MyDb ("c:\\Data\\MyDb .mdf");
var user = =
(from u in MyDb.loginInfos
where u.username== txtUsername.Text
select u).SingleOrDefault();
// user.username
I'm developing a C# library with .NET Framework 4.0 and Entity Framework 6.1.3.
I want to get the same result that this sql statement:
select c.CODE_LEVEL
from CODES c
where c.CODE in
(Select CODE
from AGGREGATION_CHILDS
where PARENT_CODE = N'1')
group by c.CODE_LEVEL
with entity framework.
I'm using repository pattern, and I have tried this:
List<AGGREGATION_CHILDS> childrenCodeLevel =
m_AggChildRepo
.SearchFor(a => a.PARENT_CODE == aggregation.PARENT_CODE).GroupBy(a => a.Code.CODE_LEVEL).SelectMany(a => a).ToList();
With this code I get a list of AGGREGATION_CHILDS and I only need CODE_LEVEL value.
SearchFor implementation:
public IQueryable<TEntity> SearchFor(Expression<Func<TEntity, bool>> predicate)
{
return _dbSet.Where(predicate);
}
This is the sql tables creation statements:
CREATE TABLE [dbo].[CODES]
(
[CODE] [nvarchar](20) NOT NULL,
[CODE_LEVEL] [tinyint] NOT NULL,
CONSTRAINT [PK_CODES] PRIMARY KEY CLUSTERED
(
[CODE] ASC
)
)
CREATE TABLE [dbo].[AGGREGATION_CHILDS]
(
[CODE] [nvarchar](20) NOT NULL,
[PARENT_CODE] [nvarchar] (20) NOT NULL,
[POSITION] [int] NOT NULL,
CONSTRAINT [PK_AGGREGATION_CHILDS] PRIMARY KEY CLUSTERED
(
[CODE] ASC
),
CONSTRAINT [FK_AGGREGATION_CHILDS_AGGREGATIONS] FOREIGN KEY ([PARENT_CODE]) REFERENCES [AGGREGATIONS]([CODE]) ON DELETE CASCADE,
CONSTRAINT [FK_AGGREGATION_CHILDS_CODES] FOREIGN KEY ([CODE]) REFERENCES [CODES]([CODE])
)
All records in AGGREGATION_CHILDS for the same PARENT_CODE will have the same CODE_LEVEL.
How can I reproduce that sql statement?
Since you are not using any aggregate the group by will just removed the duplicates, same as using Distinct.
var res = db.CODES.Where(x =>
db.AGGREGATION_CHILDS.Any(y => y.PARENT_CODE == 1 && x.Code == y.Code))
.Select(x => x.CODE_LEVEL)
.Distinct();
Fairly new to LINQ and am trying to figure out how to write a particular query. I have a database where each CHAIN consists of one or more ORDERS and each ORDER consists of one or more PARTIALS. The database looks like this:
CREATE TABLE Chain
(
ID int NOT NULL PRIMARY KEY CLUSTERED IDENTITY(1,1),
Ticker nvarchar(6) NOT NULL,
Company nvarchar(128) NOT NULL
)
GO
CREATE TABLE [Order]
(
ID int NOT NULL PRIMARY KEY CLUSTERED IDENTITY(1,1),
Chart varbinary(max) NULL,
-- Relationships
Chain int NOT NULL
)
GO
ALTER TABLE dbo.[Order] ADD CONSTRAINT FK_Order_Chain
FOREIGN KEY (Chain) REFERENCES dbo.Chain ON DELETE CASCADE
GO
CREATE TABLE Partial
(
ID int NOT NULL PRIMARY KEY CLUSTERED IDENTITY(1,1),
Date date NOT NULL,
Quantity int NOT NULL,
Price money NOT NULL,
Commission money NOT NULL,
-- Relationships
[Order] int NOT NULL
)
GO
ALTER TABLE dbo.Partial ADD CONSTRAINT FK_Partial_Order
FOREIGN KEY ([Order]) REFERENCES dbo.[Order] ON DELETE CASCADE
I want to retrieve the chains, ordered by the earliest date among all the partials of all the orders for each particular chain. In T-SQL I would write the query as this:
SELECT p.DATE, c.*
FROM CHAIN c
CROSS APPLY
(
SELECT DATE = MIN(p.Date)
FROM PARTIAL p
JOIN [ORDER] o
ON p.[ORDER] = o.ID
WHERE o.CHAIN = c.ID
) AS p
ORDER BY p.DATE ASC
I have an Entity Framework context that contains a DbSet<Chain>, a DbSet<Order>, and a DbSet<Partial>. How do I finish this statement to get the result I want?:
IEnumerable<Chain> chains = db.Chains
.Include(c => c.Orders.Select(o => o.Partials))
.[WHAT NOW?]
Thank you!
.[WHAT NOW?]
.OrderBy(c => c.Orders.SelectMany(o => o.Partials).Min(p => p.Date))
Here c.Orders does join Chain to Order, while o.SelectMany(o => o.Partials) does join Order to Partial. Once you have access to Partial records, you can use any aggregate function, like Min(p => p.Date) in your case.
I am trying to figure out the proper query in linq to sql, but I just cant figure out how to do so. Lets say I have a table with the following (this table basically is a one to many relationship)
Id (PK) | SupervisorId | EmployeeId
1 1 5
2 1 6
3 1 7
4 2 5
5 2 6
6 3 7
7 4 7
8 4 8
I want my linq to sql query to find the supervisorId which has for employeeId 5 and 6. The query would return 2 only. I could use 2 where clause, but lets say I would want to input 3 employeeIds, my query would have to modified. If the passed permutation doesnt exist for one matched SupervisorId (ex: 5,6,8 in this case), the result would be null or empty.
The function would look like this:
int FindSuperVisorId(List<int> employeeIds);
I really dont know where to start in linq to sql for this type of scenario.
Thanks
So I'm pretty sure that this query should be converted property to LINQ to SQL, but I'm not completely sure.
So first we group by supervisor so that we have sequences of employees for that supervisor. Then we use Except with the employees you're interested in in both directions. If the the count of both of those Except calls is zero then the sets are exactly equal. There are more efficient ways of determining if two sets are equal in linq-to-objects, but I doubt they would be properly converted to SQL code.
var supervisorId = table.GroupBy(item => item.SupervisorId)
.Select(group => new
{
additionalItems = group.Select(item => item.EmployeeId).Except(employees),
missingItems = employees.Except(group.Select(item => item.EmployeeId)),
group = group
})
.Where(queries => queries.additionalItems.Count() == 0
&& queries.missingItems.Count() == 0)
.Select(queries => queries.group.Key)//gets the supervisorID
.FirstOrDefault();
I had to model your table as a many-many relationship as follows:
CREATE TABLE [dbo].[Employee](
[Name] [nvarchar](50) NOT NULL,
[Id] [int] IDENTITY(1,1) NOT NULL,
CONSTRAINT [PK_Employee] PRIMARY KEY CLUSTERED
(
[Id] ASC
)
CREATE TABLE [dbo].[SupervisorEmployees](
[SupervisorId] [int] NOT NULL,
[EmployeeId] [int] NOT NULL,
CONSTRAINT [PK_SupervisorEmployees] PRIMARY KEY CLUSTERED
(
[SupervisorId] ASC,
[EmployeeId] ASC
)
GO
ALTER TABLE [dbo].[SupervisorEmployees] WITH CHECK ADD CONSTRAINT [FK_SupervisorEmployees_Employee] FOREIGN KEY([SupervisorId])
REFERENCES [dbo].[Employee] ([Id])
GO
ALTER TABLE [dbo].[SupervisorEmployees] CHECK CONSTRAINT [FK_SupervisorEmployees_Employee]
GO
ALTER TABLE [dbo].[SupervisorEmployees] WITH CHECK ADD CONSTRAINT [FK_SupervisorEmployees_Employee1] FOREIGN KEY([EmployeeId])
REFERENCES [dbo].[Employee] ([Id])
GO
ALTER TABLE [dbo].[SupervisorEmployees] CHECK CONSTRAINT [FK_SupervisorEmployees_Employee1]
GO
Then using Entity Framework database first (not Linq to SQL unfortunately) the following LINQPad code works fine:
void Main()
{
FindSupervisorIds( new List<int>{5,6} ).Dump();
}
IEnumerable<int> FindSupervisorIds(List<int> employeeIds)
{
// two Excepts to do 'sequence equals'
var supervisors = Employees.Where (e =>
!e.Employees.Select (em => em.Id).Except(employeeIds).Any()
&& !employeeIds.Except(e.Employees.Select (em => em.Id)).Any()
);
return supervisors.Select (s => s.Id).Distinct();
}
int? FindSupervisorId(List<int> employeeIds)
{
var supervisors = FindSupervisorIds(employeeIds).ToList();
if(supervisors.Count == 1)
{
return supervisors.First ();
}
return null;
}
FindSupervisorIds generates a single SQL query. If you need to check there's only one matching supervisor it's probably best to call ToList() on the returned list of supervisors as in FindSupervisorId.
Trying to do the same thing with LINQ to SQL fails due to the calls to Except with the exception
'NotSupportedException: Local sequence cannot be used in LINQ to SQL implementations of query operators except the Contains operator.'
one possibility:
public int FindSuperVisorId(IEnumerable<Employee> employes)
{
var distinctSupervisors = employes.Select(e => e.SuperVisor).Distinct();
var superVisor = distinctSupervisors.Where(supervisor => employes.All(employee => employee.SuperVisor.Equals(supervisor))).FirstOrDefault();
return superVisor;
}
and in case you want all matches of same supervisors:
public IEnumerable<int> FindSuperVisorId(IEnumerable<Employee> employes)
{
var distinctSupervisors = employes.Select(e => e.SuperVisor).Distinct();
var equalSupervisors = distinctSupervisors .Where(supervisor => employes.All(employee => employee.SuperVisor.Equals(supervisor)));
return equalSupervisors;
}
or directly:
public IEnumerable<int> FindSuperVisorId(IEnumerable<Employee> employes)
{
return employes.Select(e => e.SuperVisor).Distinct()
.Where(supervisor => employes.All(employee => employee.SuperVisor.Equals(supervisor)));
}