算法 - Partition Labels

Partition Labels

A string S of lowercase letters is given. We want to partition this string into as many parts as possible so that each letter appears in at most one part, and return a list of integers representing the size of these parts.

Example 1:

Input: S = “ababcbacadefegdehijhklij”
Output: [9,7,8]
Explanation:
The partition is “ababcbaca”, “defegde”, “hijhklij”.
This is a partition so that each letter appears in at most one part.
A partition like “ababcbacadefegde”, “hijhklij” is incorrect, because it splits S into less parts.

Note:

S will have length in range [1, 500].
S will consist of lowercase letters (‘a’ to ‘z’) only.

Solution: 

随机给定一个字符串序列,按规则分段,保证每个字母只出现在其中一个序列中

思路:

  • 用map来存储给定字母的最后一个下标
#include <string>
#include <vector>
#include <map>
//#include <tr1/unordered_map>
#include <iostream>
using namespace std;
//using namespace std::tr1;

map<int, string> splitString(string& str)
{
    map<char,int> srcmp;
    map<int, string> res;

    if (str.empty()) return res;

    for(int i = 0; i < str.size(); i++) srcmp[str[i]] = i;

    for(int j = 0; j < str.size(); j++)
    {
        int pos = max(j, srcmp[str[j]]);
        res.insert(make_pair<int, string>(pos -j + 1, str.substr(j, pos -j + 1)));
        while(j != pos) {
            j++;
        }
    }
    return res;
}


int main()
{
    string str = "abcdaembuijejjdfslfdoefetjljroglwfjfwlfjosiff";
    map<int, string> res = splitString(str);
    map<int, string>::iterator it = res.begin();

    cout << "Original String: " << str << endl;
    while(it != res.end())
    {
        cout << it->first << ": " << it->second << endl;
        it++;
    }

    cout << endl;
    return 1;
}

小注:

在C++早期版本标准库里面只有map这个字典,内部实现是采用的红黑树。对于字典这类结构也可以用hash表来实现,也就是C++的标准库应该也要有hash_map这种数据结构。

  • 红黑树实现的map占用内存较小,但是查找效率不高,O(logn)的查找效率。
  • hash表实现的map占用内存较大,但是查找效率高,往往可以逼近O(1)的惊人查找效率。

在C++中关于map的hash表方法的实现是unordered_map这个数据结构,首次出现应该是在C++98那个年代的tr1这个命名空间里面出现:

#include <tr1/unordered_map>
using std::tr1::unordered_map;

c++0x/c++11标准才把unordered_map纳入std标准, 也就是只有在支持-std=c++0x甚至-std=c++11的编译器里(对于g++来说大概是g++4.4这个版本以上的才开始支持),才可以用如下代码使用unordered_map:

#include <unordered_map>
using std::unordered_map;

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: 以下是Louvain算法的Matlab实现: ```matlab function [C,Q]=louvain(A) % Input: A: adjacency matrix of the network % Output: C: community structure % Q: modularity n=length(A); m=sum(sum(A)); k=sum(A); B=A-m'*m/(2*m); C=1:n; Q=0; while 1 [Ci,Qi]=modularity(C,B); if Qi-Q<1e-10 break end for i=1:max(Ci) nodes=find(Ci==i); B(nodes,nodes)=B(nodes,nodes)-sum(sum(A(nodes,nodes)))/(2*m); end [C,Q]=reindex(Ci,Qi); end function [C,Q]=modularity(C,B) m=length(C); mk=C'*C; Q=0; for i=1:m ki=sum(B(i,:)); if ki>0 Q=Q+(B(i,:)*C==C(i))*(1-mk(i)/(2*m))/2/ki; end end function [C,Q]=reindex(C,Q) A=unique(C); B=zeros(max(A),1); B(A)=1:length(A); C=B(C); ``` 调用方式如下: ```matlab [C,Q]=louvain(A); ``` 其中,A为邻接矩阵,C为社区划分结果,Q为模块度。这个函数使用了Matlab自带的unique函数,因此需要注意输入的邻接矩阵A必须是非负整数矩阵。 ### 回答2: Louvain算法是一种常用于社区发现的图分析算法。它通过不断优化社区结构的方式,将图中的节点划分为不同的社区。下面是Louvain算法在Matlab中的实现步骤: 1. 构建图:首先,根据图的节点和边的信息,通过Matlab中的图数据结构来表示图。 2. 初始化社区:将每个节点作为一个单独的社区,并为每个节点分配一个唯一的社区标识符。 3. 迭代优化:在每一轮迭代中,遍历图中的每个节点,计算将该节点移动到相邻节点所属社区所带来的模块度增益。 4. 社区合并:找出具有最大模块度增益的节点,并将其移动到相邻节点所属的社区中。同时,更新其他节点的社区标识符。 5. 终止条件:如果在当前轮迭代中没有任何节点发生社区变化,停止迭代。 6. 输出结果:返回最终优化后的社区划分结果。 在Matlab中,可以使用类似以下的伪代码实现Louvain算法: ``` 1. 构建图 2. 初始化社区 3. while(true) 4. for each node in graph 5. for each neighbor of node 6. calculate modularity gain by moving node to neighbor's community 7. find node with the maximum modularity gain 8. if the maximum modularity gain is non-positive 9. break 10. move the node to the community of its neighbor with the maximum modularity gain 11. update community labels for other nodes 12. end while 13. return the optimized community partition ``` 这是一个简单的Louvain算法实现,可以根据具体的需求进行优化和改进。 ### 回答3: Louvain算法是一种用于发现社区结构的层次聚类算法,可用于图数据的社区检测。这个算法的主要思想是将图中的节点进行合并,从而形成更大的社区,直到无法再合并为止,得到最终的社区划分结果。 在使用Matlab实现Louvain算法之前,我们首先需要导入图数据,可以使用Matlab的图对象来表示图数据。接下来,我们可以按照以下步骤实现Louvain算法: 1. 初始化每个节点为一个单独的社区,并计算图的模块度Q。 2. 遍历每个节点,计算将其与其邻居节点合并后的模块度增益值。 3. 找到增益值最大的节点,将其与邻居节点合并,更新社区划分。 4. 重复步骤2和步骤3,直到没有节点可以合并为止。 5. 得到最终的社区划分结果。 在实现过程中,我们需要使用一些辅助函数来进行计算,如计算社区的模块度、计算节点的度等。此外,我们还需要用到循环和条件判断语句来实现算法的迭代过程。 实现Louvain算法时,还可以通过优化算法的效率和准确性来改进算法,如限制迭代次数、添加终止条件等。 总而言之,Louvain算法的Matlab实现可以通过使用图对象、计算模块度和增益值、节点合并等步骤来实现。通过编写相应的函数和循环迭代,我们可以得到图数据的社区划分结果。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值