当前位置:编程学习 > C#/ASP.NET >>

统计用户点击次数

 if (!Page.IsPostBack)
        {

            dh.ExecuteNonQuery("update notice set clicks=clicks+1 where noticeid=@noticeid");//更新点击次数
        }
我是主要写代码的。。
但当用户打开页面, 不断刷新,   次数也变成累加了,             有什么好办法解决刷新问题吗?   或者有好的思路统计访问次数 --------------------编程问答-------------------- 顶 --------------------编程问答-------------------- 重定向,禁用按钮之类的。如果希望用户点击之后还在原来页面并且可以继续点击,那最好的办法就是重写一个Page类和一个实现IHttpModule的类。下面是我从网上搜到的代码,但实际应用中会出现问题,希望楼主慎重。
using System;
using System.Data;
using System.Configuration;
using System.Web;
using System.Web.Security;
using System.Web.UI;
using System.Web.UI.WebControls;
using System.Web.UI.WebControls.WebParts;
using System.Web.UI.HtmlControls;
using System.Collections;

/// <summary>
/// BasePage 的摘要说明
/// </summary>
public class BasePage:System.Web.UI.Page
{
public BasePage()
{
//
// TODO: 在此处添加构造函数逻辑
//
    }
    #region IsRefreshed
    public bool IsRefreshed
    {
        get
        {
            string requestPath = HttpContext.Current.Request.Path;
            return (bool)HttpContext.Current.Items[requestPath + "_IsRefreshed"];
        }
    }
    #endregion
    protected override void  OnPreRenderComplete(EventArgs e)
    {
        base.OnPreRenderComplete(e);
        string requestPath = HttpContext.Current.Request.Path;
        int ticket = int.Parse(HttpContext.Current.Items[requestPath + "_NextTicket"].ToString());
        ClientScript.RegisterHiddenField("CurrentTicket", ticket.ToString());
    }
}

public class NoRepeatOperModel : IHttpModule
{
    public NoRepeatOperModel()
    {
    }
    static Hashtable historyRequest = null;
    private string RequestPath
    {
        get
        {
            return HttpContext.Current.Request.Path;
        }
    }
    #region IHttpModel 成员
    public void Dispose()
    {
    }
    public void Init(HttpApplication context)
    {
        if (historyRequest == null)
        {
            historyRequest = new Hashtable();
        }
        context.BeginRequest += delegate(object sender, EventArgs e)
        {
            int lastTicket = GetLastTicket();
            int currentTicket = GetCurrentTicket(lastTicket);
            if (currentTicket > lastTicket || (lastTicket == currentTicket && currentTicket == 0))
            {
                HttpContext.Current.Items[RequestPath + "_IsRefreshed"] = false;
                historyRequest[RequestPath] = currentTicket;
            }
            else
            {
                HttpContext.Current.Items[RequestPath + "_IsRefreshed"] = true;
            }
        };
    }
    #endregion
    private int GetLastTicket()
    {
        if (!historyRequest.ContainsKey(RequestPath))
        {
            return 0;
        }
        return int.Parse(historyRequest[RequestPath].ToString());
    }
    private int GetCurrentTicket(int LastTicket)
    {
        int ticket;
        string currentTicket = HttpContext.Current.Request["CurrentTicket"];
        if (currentTicket == null)
        {
            ticket = LastTicket;
        }
        else
        {
            ticket = int.Parse(currentTicket);
        }
        //保存下一个标号
        HttpContext.Current.Items[RequestPath + "_NextTicket"] = ticket + 1;
        return ticket + 1;
    }
}
--------------------编程问答-------------------- 是想达到什么目的呢?  每个用户只能点击一次? 还是什么? --------------------编程问答-------------------- 时间做判断,20秒内刷新不 +1 --------------------编程问答-------------------- 定时刷新页面 --------------------编程问答-------------------- 我是想要, 当用户打开页面的时候, +1 , 但是用户不停刷新页面的时候不加 --------------------编程问答-------------------- 顶 --------------------编程问答-------------------- 用session啊!大哥... --------------------编程问答--------------------
引用 6 楼 wangpenglipei1 的回复:
我是想要, 当用户打开页面的时候, +1 , 但是用户不停刷新页面的时候不加

在打开这个页面之前加一个空的页面,把 +1 写在空的页面,这样刷新数就不会加了。 --------------------编程问答--------------------
引用 8 楼 angusn 的回复:
用session啊!大哥...


不想要SESSION  或COOKIES     因为是新闻列表, 太多了  SESSION 给服务器负担 --------------------编程问答--------------------
引用 9 楼 phf0313 的回复:
引用 6 楼 wangpenglipei1 的回复:
我是想要, 当用户打开页面的时候, +1 , 但是用户不停刷新页面的时候不加

在打开这个页面之前加一个空的页面,把 +1 写在空的页面,这样刷新数就不会加了。


貌似不错, 还有更好的吗 --------------------编程问答-------------------- 进来学习下 同时帮顶 --------------------编程问答-------------------- //在主页的PageLoad事件里写如下事件
protected void PageLoad(object sender,eventArgs e)
{
    if(Session["count"] != null)
    {
        int count = 0;
        Session["count"] = count;
        string sID = Session["count"].SessionID;
        if(!IsPostBack)
        {
            if(Session["count"].SessionID != sID)
            {
              count = count + 1;
            }
        }
    }
}

这样子,也可以用Application做,
判断SessionID是否是同一个人,可以做到防止刷新,不过要做的彻底,还需要用IP来判断 --------------------编程问答-------------------- 不想用 session  和cookies 来处理,寻求好 方法 --------------------编程问答-------------------- if(!IsPostBack) 
        { 
dh.ExecuteNonQuery("update notice set clicks=clicks+1 where noticeid=@noticeid");//更新点击次数 
}

为什么用户F5刷新页面也会执行里面的代码呢 --------------------编程问答-------------------- --------------------编程问答-------------------- 用session可以啊
--------------------编程问答-------------------- 按F5了,就应该是相当于重新加载了这个页面,不是回发,肯定要执行了 --------------------编程问答--------------------
引用 18 楼 xyyz150 的回复:
按F5了,就应该是相当于重新加载了这个页面,不是回发,肯定要执行了


看来我 回发 和 页面刷新还搞不太懂哦 --------------------编程问答--------------------
引用 9 楼 phf0313 的回复:
引用 6 楼 wangpenglipei1 的回复:
 我是想要, 当用户打开页面的时候, +1 , 但是用户不停刷新页面的时候不加

 在打开这个页面之前加一个空的页面,把 +1 写在空的页面,这样刷新数就不会加了。

对,这个方法不错啊,直接在第一个页面把信息的ID传过来,再在空页面+1,最后再跳到信息显示的页面 --------------------编程问答--------------------
引用 20 楼 pgameli 的回复:
引用 9 楼 phf0313 的回复:
 引用 6 楼 wangpenglipei1 的回复:
  我是想要, 当用户打开页面的时候, +1 , 但是用户不停刷新页面的时候不加

  在打开这个页面之前加一个空的页面,把 +1 写在空的页面,这样刷新数就不会加了。

 对,这个方法不错啊,直接在第一个页面把信息的ID传过来,再在空页面+1,最后再跳到信息显示的页面

把这个空页面做成通用页面,所有的信息都可以通过这个空页面来更新点击次数了 --------------------编程问答-------------------- 回发是用户点击页面上的按钮或选择框等,需要再次回到服务器一次时,才叫回发

刷新,你可以理解为:我数据库里的内容已更新,你页面一定要重新生成(就像别人第一次讯问该页面一样的道理),这时候IIS会清除缓存中已有的该页面的旧版本,重新生成一个新页面对象


如果你不想用Cookie或session,那么可以用反技术

就是把代码必为:
Server.Transfer(this.Page.ResolveClientUrl);
if (Page.IsPostBack) //注意这里已更换
        { 

            dh.ExecuteNonQuery("update notice set clicks=clicks+1 where noticeid=@noticeid");//更新点击次数 
        } 
--------------------编程问答-------------------- 但以上有个问题,就是你不能在该页面中放入能点击的按钮或会回发的选择框 --------------------编程问答-------------------- 近来学习 --------------------编程问答--------------------
引用 22 楼 likevs 的回复:
回发是用户点击页面上的按钮或选择框等,需要再次回到服务器一次时,才叫回发

刷新,你可以理解为:我数据库里的内容已更新,你页面一定要重新生成(就像别人第一次讯问该页面一样的道理),这时候IIS会清除缓存中已有的该页面的旧版本,重新生成一个新页面对象


如果你不想用Cookie或session,那么可以用反技术

就是把代码必为:
Server.Transfer(this.Page.ResolveClientUrl);
if (Page.IsPostBack) //注意这里已更换
        {

            dh.ExecuteNonQuery("update notice set clicks=clicks+1 where noticeid=@noticeid");//更新点击次数
        }


Server.Transfer(this.Page.ResolveClientUrl);  错误了, --------------------编程问答-------------------- 哎,如果没什么好办法,就只能刷新也加1了、用户也没那么无聊狂刷 --------------------编程问答-------------------- ding --------------------编程问答-------------------- 记录用户登录日志,一个IP一定时间内刷新只记录一次,
如同很多网站的投票系统
--------------------编程问答-------------------- ding --------------------编程问答-------------------- 把你的代码,放到这个事件里试试。
protected void Page_Init(object sernder, EventArgs e)
    {
if (!Page.IsPostBack) 
        { 

            dh.ExecuteNonQuery("update notice set clicks=clicks+1 where noticeid=@noticeid");//更新点击次数 
        } 

    } --------------------编程问答-------------------- 用session提供的功能不就行了 --------------------编程问答-------------------- 如果你是N时间内可以增加一次的话,
可以把对方的IP添加到cache,存的是数组或者集合。
然后判断就行了。
给cache设置时间过期就OK了。 --------------------编程问答--------------------
引用 32 楼 cam6778102 的回复:
如果你是N时间内可以增加一次的话,
可以把对方的IP添加到cache,存的是数组或者集合。
然后判断就行了。
给cache设置时间过期就OK了。

具体点就是,把所有人员的IP都存进cache,然后循环判断,存在则跳过,否则增加1.
cache存在服务器,设置时间过期,比如1天过期一次,第2天就可以增加访问次数了。 --------------------编程问答--------------------
引用楼主 wangpenglipei1 的回复:
if (!Page.IsPostBack)
        {

            dh.ExecuteNonQuery("update notice set clicks=clicks+1 where noticeid=@noticeid");//更新点击次数
        }
我是主要写代码的。。
但当用户打开页面, 不断刷新,  次数也变成累加了,            有什么好办法解决刷新问题吗?  或者有好的思路统计访问次数


首先集中于尽可能具体的数据库数据一致性检验范围来处理,很简单。你可以在页面 Page 的 PreRender 事件处理程序中,将 clicks 从数据库中读出来并且保存到 ViewState,类似于:

private int Clicks
{
   get{ object x=ViewState["Clicks"]; return x==null?0:(int)x; }
   set{ ViewState["Clicks"]=value ; }
}

protected void Page_PreRender(object sender, EventArgs e)
{
    Clicks=读取数据库中的Clicks();
}


然后你的那个 SQL 就可以改为来验证页面上的Clicks是否正好是你写出去的,类似于:
if (!Page.IsPostBack) 

      if(Clicks!=读取数据库中的Clicks())
            处理_此时提交的页面信息不是最后一次输出的页面();
      else
            dh.ExecuteNonQuery("update notice set clicks=clicks+1 where noticeid=@noticeid");//更新点击次数 


或者你也可以写::
if (!Page.IsPostBack) 

      dh.ExecuteNonQuery("update notice set clicks=clicks+1 where clicks=@ViewStateClicksValue && noticeid=@noticeid");//更新点击次数 

--------------------编程问答-------------------- and --------------------编程问答-------------------- sp1234说的方法不错啊,可以参考下 --------------------编程问答-------------------- 嘿嘿,看见高人回答了,试下
补充:.NET技术 ,  ASP.NET
CopyRight © 2012 站长网 编程知识问答 www.zzzyk.com All Rights Reserved
部份技术文章来自网络,