zoukankan      html  css  js  c++  java
  • (线段树区间赋值)CSU 1942

    题意:

    一个串(串中只有26个小写字母),选一个区间进行排序,进行100000次,输出最后的串。

    分析:

    比赛的时候很懵逼,感觉这题跟之前的额大崩龙有点像,但是没多想,也怪自己太菜了。

    确实是真的像,甚至是一模一样啊。

    对于每次排序只需要进行一次类似计数排序的的操作即可,26个字符,进行26次区间赋值即可。理论上时间能过得去。

    代码:

      1 #include <queue>
      2 #include <string>
      3 #include <cstdio>
      4 #include <cstring>
      5 #include <iostream>
      6 #include <algorithm>
      7 #include <map>
      8 
      9 
     10 using namespace     std;
     11 
     12 typedef long long ll;
     13 typedef unsigned long long ull;
     14 typedef pair<int, int> pii;
     15 typedef pair<ull, ull> puu;
     16 
     17 #define inf (0x3f3f3f3f)
     18 #define lnf (0x3f3f3f3f3f3f3f3f)
     19 #define eps (1e-8)
     20 #define fi first
     21 #define se second
     22 
     23 //--------------------------
     24 
     25 const ll mod = 1000000007;
     26 const int maxn = 100010;
     27 
     28 
     29 char str[maxn];
     30 int n;
     31 int q;
     32 
     33 struct Node {
     34     int left, right;
     35     int num[26];
     36     int lazy;
     37 } node[maxn << 2];
     38 
     39 void push_up(int n) {
     40     for(int i = 0; i < 26; i++) {
     41         node[n].num[i] = node[n << 1].num[i] + node[n << 1 | 1].num[i];
     42     }
     43 }
     44 
     45 void push_down(int n) {
     46     if(node[n].lazy != -1) {
     47         node[n << 1].lazy = node[n << 1 | 1].lazy = node[n].lazy;
     48         memset(node[n << 1].num, 0, sizeof(node[n << 1].num));
     49         memset(node[n << 1 | 1].num, 0, sizeof(node[n << 1 | 1].num));
     50         node[n << 1].num[node[n].lazy] = (node[n].right - node[n].left + 1) - (node[n].right - node[n].left + 1) / 2;
     51         node[n << 1 | 1].num[node[n].lazy] = (node[n].right - node[n].left + 1) / 2;
     52         node[n].lazy = -1;
     53     }
     54 }
     55 
     56 void update(int n, int left, int right, char val) {
     57     if(node[n].left >= left && node[n].right <= right) {
     58         node[n].lazy = val - 'a';
     59         memset(node[n].num, 0, sizeof(node[n].num));
     60         node[n].num[node[n].lazy] = node[n].right - node[n].left + 1;
     61         return ;
     62     }
     63     push_down(n);
     64     int mid = (node[n].left + node[n].right) >> 1;
     65     if(mid >= left)update(n << 1, left, right, val);
     66     if(mid < right)update(n << 1 | 1, left, right, val);
     67     push_up(n);
     68 }
     69 
     70 int query(int n, int left, int right, char val) {
     71     if(node[n].left >= left && node[n].right <= right) {
     72         return node[n].num[val - 'a'];
     73     }
     74     push_down(n);
     75     int mid = (node[n].left + node[n].right) >> 1;
     76     int sum = 0;
     77     if(mid >= left)sum += query(n << 1, left, right, val);
     78     if(mid < right)sum += query(n << 1 | 1, left, right, val);
     79     return sum;
     80 }
     81 
     82 
     83 void build(int n, int left, int right) {
     84     node[n].left = left;
     85     node[n].right = right;
     86     node[n].lazy = -1;
     87     if(left == right) {
     88         node[n].num[str[left] - 'a'] = 1;
     89         return ;
     90     }
     91     int mid = (left + right) >> 1;
     92     build(n << 1, left, mid);
     93     build(n << 1 | 1, mid + 1, right);
     94     push_up(n);
     95 }
     96 
     97 void print(int n) {
     98     if(node[n].left == node[n].right) {
     99         for(int i = 0; i < 26; i++) {
    100             if(node[n].num[i] != 0) {
    101                 printf("%c", i + 'a');
    102                 break;
    103             }
    104         }
    105         return ;
    106     }
    107     push_down(n);
    108     print(n << 1);
    109     print(n << 1 | 1);
    110 }
    111 
    112 void solve() {
    113     while(~scanf("%d%d", &n, &q)) {
    114         memset(node, 0, sizeof(node));
    115         scanf("%s", str + 1);
    116         build(1, 1, n);
    117         while(q--) {
    118             int l, r, op;
    119             scanf("%d%d%d", &l, &r, &op);
    120             int num[26] = {0};
    121             for(int i = 0; i < 26; i++) {
    122                 num[i] = query(1, l, r, i + 'a');
    123             }
    124             if(op == 1) {
    125                 for(int i = 0; i < 26; i++) {
    126                     if(num[i] > 0) {
    127                         update(1, l, l + num[i] - 1, i + 'a');
    128                         l += num[i];
    129                     }
    130                 }
    131             } else {
    132                 for(int i = 25; i >= 0; i--) {
    133                     if(num[i] > 0) {
    134                         update(1, l, l + num[i] - 1, i + 'a');
    135                         l += num[i];
    136                     }
    137                 }
    138             }
    139         }
    140         print(1);
    141         puts("");
    142     }
    143 
    144 
    145 
    146 }
    147 
    148 int main() {
    149 #ifndef ONLINE_JUDGE
    150     freopen("1.in", "r", stdin);
    151     freopen("1.out", "w", stdout);
    152 #endif
    153     solve();
    154     return 0;
    155 }
  • 相关阅读:
    强化学习的基本迭代方法
    基于文本描述的事务聚类
    学习强化学习之前需要掌握的3种技能
    其它 华硕 ASAU S4100U 系统安装 win10安装 重装系统 Invalid Partition Table 解决
    数据分析 一些基本的知识
    Python 取样式的内容 合并多个文件的样式 自定义样式
    电商 Python 生成补单公司需要的评论格式3
    SpringBlade 本地图片上传 生成缩略图
    SQL Server 字符串截取
    SpringBlade 本地图片上传
  • 原文地址:https://www.cnblogs.com/tak-fate/p/6965329.html
Copyright © 2011-2022 走看看