1 #include <cstdio>
2 #include <iostream>
3 #include <cstring>
4 #define ll long long
5 using namespace std;
6 const ll mo=1e9+7,N=100010,inf=1e9;
7 struct edge{ll l,r,v,x,y;}tree[N*60];
8 ll a[N],l[N],r[N],k[N],n,cnt,d,o,ans;
9 ll ksm(ll a,ll b)
10 {
11 ll r=1;
12 for (;b;b>>=1,a=a*a%mo) if (b&1) r=r*a%mo;
13 return r;
14 }
15 void work(ll &d,ll l,ll r,ll L,ll R)
16 {
17 if (!d) d=++cnt;
18 (tree[d].x+=L)%=mo,(tree[d].y+=R)%=mo,(tree[d].v+=(r-l+1)*R)%=mo;
19 if ((l+r)&1) o=(r-l+1)/2*(r+l)%mo; else o=(r+l)/2*(r-l+1)%mo;
20 (tree[d].v+=o*L)%=mo;
21 }
22 void down(ll d,ll l,ll r)
23 {
24 if (tree[d].x||tree[d].y)
25 {
26 ll mid=l+r>>1;
27 work(tree[d].l,l,mid,tree[d].x,tree[d].y),work(tree[d].r,mid+1,r,tree[d].x,tree[d].y);
28 tree[d].x=tree[d].y=0;
29 }
30 }
31 void insert(ll &d,ll l,ll r,ll L,ll R,ll x,ll y)
32 {
33 if (R<l||L>r) return;
34 if (!d) d=++cnt;
35 if (L<=l&&r<=R) work(d,l,r,x,y);
36 else
37 {
38 ll mid=l+r>>1; down(d,l,r);
39 insert(tree[d].l,l,mid,L,R,x,y),insert(tree[d].r,mid+1,r,L,R,x,y);
40 tree[d].v=(tree[tree[d].l].v+tree[tree[d].r].v)%mo;
41 }
42 }
43 ll Query(ll d,ll l,ll r,ll L,ll R)
44 {
45 if (R<l||L>r) return 0;
46 if (L<=l&&r<=R) return tree[d].v;
47 ll mid=l+r>>1; down(d,l,r);
48 return (Query(tree[d].l,l,mid,L,R)+Query(tree[d].r,mid+1,r,L,R))%mo;
49 }
50 int main()
51 {
52 freopen("sort.in","r",stdin),freopen("sort.out","w",stdout);
53 scanf("%lld",&n);
54 for (ll i=1;i<=n;i++) scanf("%lld%lld%lld",&a[i],&l[i],&r[i]);
55 for (ll i=1;i<=n;i++)
56 {
57 ll ny=ksm(r[i]-l[i]+1,mo-2);
58 k[i]=Query(d,0,inf,l[i],r[i])*ny%mo;
59 insert(d,0,inf,r[i]+1,inf,0,1),insert(d,0,inf,l[i],r[i],ny,(mo-(l[i]-1)*ny%mo)%mo);
60 }
61 d=0;
62 for (ll i=1;i<=cnt;i++) tree[i].x=tree[i].y=tree[i].v=tree[i].l=tree[i].r=0;
63 cnt=0;
64 for (ll i=n;i;i--)
65 {
66 ll ny=ksm(r[i]-l[i]+1,mo-2);
67 (k[i]+=Query(d,0,inf,l[i],r[i])*ny%mo)%=mo;
68 insert(d,0,inf,r[i]+1,inf,0,1),insert(d,0,inf,l[i],r[i],ny,(mo-l[i]*ny%mo)%mo);
69 }
70 for (ll i=1;i<=n;i++) ans=(ans+(k[i]+1)*a[i])%mo;
71 printf("%lld",ans);
72 }