Hai guys,
I have nearly 20 pages in my website .... Every page has a gridview which has thousands of records bind to it... Now i want to implement custom pagination to all those grids.... Guys can some one give a pagination class which can be reusable for all those pages
Your not really going to get a one size fits all class to do this, thats why its called custom paging.
Just a rough guide as to how I have implemented this in the past.
Store the current page number somewhere Querystring/Session/Wherever
When you call your data method/stored procedure to ask for the data pass in the page number and amount of records per page you want.
ammend you stored procedure/data method to only return records in these bounds, it will also need to return a count of the total records so the application knows how many pages there are.
Here is simple example of how you could achieve paging in your stored procedures using SQL2005/2008 (Slightly more to it in 2000)
CREATE PROCEDURE GetTowns
(
#OutTotalRecCount INT OUTPUT,
#CurrentPage INT,
#PageSize INT
)
AS
SELECT * FROM
(
SELECT
ROW_NUMBER() OVER (ORDER BY TownName) AS Row,
TownId,
TownName
FROM Towns
) AS TownsWithRowNumbers
WHERE Row >= (#CurrentPage - 1) * #PageSize + 1 AND Row <= #CurrentPage*#PageSize
SELECT #OutTotalRecCount = COUNT(*) FROM Towns
Not sure about a "class", but here are a couple of links:
.NET 3.5
.NET 2.0
p.s. If you use DataSet as your DataSource, paging and sorting is supported out of the box.
Related
I am working on a desktop application in C#. I am very new to SQL Server.
First of all I would like apologize for the question I am asking may be relevant to the questions asked before on this topic, but I searched on the internet and did not find any answer for the problem.
There is a table in my database named BillingTemp. Columns are
Bill No, Package, Type, DiscPer, TotalAmt, BillDate, TaxAmt
BillNo may repeat as there are multiple entries in a specific bill.
Now on a button click, TotalAmt and type values in this table should be updated in only first row of a table as per my logic in the code.
How can I do this? Can anyone suggest query for this?
Try this
;WITH TOP1 AS
(
SELECT TOP 1 *
FROM TABLE
WHERE BillNo = #BillNo
ORDER BY ID -- I assume you always want to update the record created first
)
UPDATE TOP1 SET TotalAmt =#TotalAmt , type = #type
I have over 10k topics in my DB table, and I count page views for each topic on session base and store only one view/per topic/per user (session time 24 hrs).
ID-----Topic----------------Views
1------Love------------------400
2------Friends---------------203
3------Birthday--------------360
Now I want to get hot topics in last 30 days, means I want to get hot topics on bases of page views in last 30 days. I just need a little direction, on how I can achieve this. Thanks
You will need to separate into a Topic table and a TopicView table if you want to truly adapt to recent views. With the current table structure there is no idea of how recent a view is - so if you have a topic spike big-time in week 10 of the year, it may remain #1 on your hot topic list for a very long time (as 'Views' column is cumulative over all-time).
CREATE TABLE Topic (
[Id] INT NOT NULL IDENTITY(1,1)
[Topic] VARCHAR(255) NOT NULL
)
CREATE TABLE TopicView (
[ViewId] INT NOT NULL IDENTITY(1,1),
[TopicId] INT NOT NULL,
[User] VARCHAR(255) NOT NULL,
[ViewDate] DATETIME NOT NULL
)
Now you can check every time a user hits a page if you have already logged a 'TopicView' for them. When you want to see what topics are hot, you could execute:
DECLARE #maxResults INT = 100 --the maximum number of results we will show
DECLARE #hotTopicViewDays INT = 30 --how recent we want to see hot topic activity
DECLARE #hotTopicViewLimit INT = 300 --what amount of views we consider hot
SELECT TOP (#maxResults)
T.[Id],
T.[Topic],
COUNT(TV.[ViewID]) [Views]
FROM [Topic] T
JOIN [TopicView] TV
ON T.[Id] = TV.[TopicId]
WHERE TV.ViewDate >= DATEADD(DAY, -(#hotTopicViewDays), GETDATE())
GROUP BY T.[Id],
T.[Topic]
HAVING COUNT(TV.[ViewId]) >= #hotTopicViewLimit
This is pretty extensible and will allow you to configure:
How many results you want to return with #maxResults
How recent views need to be to factor into "hot topic" activity with #hotTopicViewDays
How much activity is required to consider a topic "hot" with #hotTopicViewLimit
Let me know if there are any questions or if anyone sees an issue with this approach.
You already store the views in the database, which is good. You'll also need to have stored the date on which the topic was created.
Provided you have done that, you can write a query like this one (I dunno your column names etc.):
SELECT *
FROM Topics t
WHERE t.DateAdded >= dateadd(day, -30, getdate())
ORDER BY t.Views DESC
It returns all topics created in the last 30 days, most viewed topics first.
You do not want to load all ten thousand records into memory so, make sure you implement pagination.
I'have a count method to paginate a grid, that return a number around 2 millions, I wan't to improve it speed with a query like this, but on Linq:
SELECT count(*)
FROM (SELECT ROW_NUMBER() OVER (ORDER BY id) AS Row, Id
FROM myTable ) t
WHERE Row between 0 and (pageSize*visiblePages)+1 -- The number 1 is to check if there is another set of 1 or more pages
My problem is, I don't need to count 2 millions for a page that will show that I have 11 pages. The method to retrieve only 10 results works fine, but I can't count with the row_number
Maybe you can use LINQ's Take or Skip like this : http://msdn.microsoft.com/en-us/library/bb386988%28v=vs.110%29.aspx
Also check this VS gallery's pager control for MVC: http://en.webdiyer.com/
Is there a way to only load the new or updated (edited) records in a table using Sql in C#?
Suppose i have a table which consists of 1000 student records.I want to show this information in a gridview ( this is just an example ) and upon adding or editing new entries,I want the gridview to get updated and show the latest changes to the table.If i go and have a
select *
statement ,This will definitely kill the application performance,So i thought its a good idea to try to add only those new records to the previously loaded records to the gridview.
But I'm clueless on the How to do such a task.
There is no other solution then simply architect you database.
Just one of many possible solutions: for every inserted or updated record in database you can have a timestamp. Having that information in database you can:
a) get the latest, from timestamp point of view, record in your DataGrid
b) get from darabase all reoirds that have timestamp bigger then it.
I repeat, this us just one of many possible solutions. What fits your requirements has to be decided by yourself.
Create a timestamp column and store the "last updated" date. Within your application, store the last time the data was retrieved from the database. Then, you can select only the records that have changed (or been added) since then.
The simplest way would be add a new field in the table such as ModifyDate of type datetime, and on insertion and updation of record put the current datetime in these field.
In that case you can select a query on the basis of this field as follows
Select Top 10 * from Table1 OrderBy ModifyDate desc
I want to get some random records from db. There is two solution for this :
1- Using TABLESAMPLE for getting data from db directly.
2- Write a method In my application for doing this. In this method we generate multiple random number and get data like this :
select * from db where ID = #RandomNumber
if this ID does not exist, I pass a new number.
Now which one has better performance?
According to the documentation for TABESAMPLE you shouldn't use it if you "really want a sample of individual rows":
If you really want a random sample of
individual rows, modify your query to
filter out rows randomly, instead of
using TABLESAMPLE. For example, the
following query uses the NEWID
function to return approximately one
percent of the rows of the
Sales.SalesOrderDetail table:
SELECT *
FROM Sales.SalesOrderDetail
WHERE 0.01 >= CAST(CHECKSUM(NEWID(), SalesOrderID) & 0x7fffffff AS float)
/ CAST (0x7fffffff AS int)
The SalesOrderID column is included in
the CHECKSUM expression so that
NEWID() evaluates once per row to
achieve sampling on a per-row basis.
The expression CAST(CHECKSUM(NEWID(),> SalesOrderID) & 0x7fffffff AS float / CAST(0x7fffffff AS int) evaluates to a random float value between 0 and 1.
Either way, given the potentially endless number of requests you could make by passing in #RandomNumber (in theory the first 1000 requests you make might return nothing), the better approach is to limit the resultset on the server.
try this:
SELECT TOP 1 * FROM db
ORDER BY NEWID()
the NewID function will generate UniqueIdentifier value and it will be random.
Source: SQL to Select a random row from a database table
I would use TABLESAMPLE, as its makes it very easy to generate sample data. I expect it would be more efficient as you only call one piece of SQL.
e.g.
USE AdventureWorks ;
GO
SELECT FirstName, LastName
FROM Person.Contact
TABLESAMPLE (10 PERCENT)
In your other example, you will have to keep on calling select * from db where ID = #RandomNumber many times.
If you after individual rows then i would use another method, some form of random TOP 1 etc...
I recommend to read a post about various methods to get random row from table. It's based on PostgreSQL, but I'm sure that 90% applies to SQL Server too.
Of course most flexible and best performing solution can be achieved by writing a stored procedure.
Cost (hence: best performance) of getting truly random sample depends on data (type of data, statistics and distribution, including sparseness).